* src/vm/jit/stacktrace.c (stacktrace_fillInStackTrace)
[cacao.git] / src / vm / vm.c
1 /* src/vm/finalizer.c - finalizer linked list and thread
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:
30
31    $Id: finalizer.c 4357 2006-01-22 23:33:38Z twisti $
32
33 */
34
35
36 #include "config.h"
37
38 #include <assert.h>
39 #include <stdlib.h>
40
41 #include "vm/types.h"
42
43 #include "mm/boehm.h"
44 #include "mm/memory.h"
45 #include "native/jni.h"
46 #include "native/native.h"
47
48 #if defined(USE_THREADS)
49 # if defined(NATIVE_THREADS)
50 #  include "threads/native/threads.h"
51 # else
52 #  include "threads/green/threads.h"
53 #  include "threads/green/locks.h"
54 # endif
55 #endif
56
57 #include "vm/classcache.h"
58 #include "vm/exceptions.h"
59 #include "vm/finalizer.h"
60 #include "vm/global.h"
61 #include "vm/initialize.h"
62 #include "vm/options.h"
63 #include "vm/properties.h"
64 #include "vm/signallocal.h"
65 #include "vm/stringlocal.h"
66 #include "vm/suck.h"
67 #include "vm/vm.h"
68 #include "vm/jit/jit.h"
69 #include "vm/jit/asmpart.h"
70 #include "vm/jit/profile/profile.h"
71 #include "vm/rt-timing.h"
72
73 #if defined(ENABLE_JVMTI)
74 #include "native/jvmti/cacaodbg.h"
75 #endif
76
77 /* Invocation API variables ***************************************************/
78
79 _Jv_JavaVM *_Jv_jvm;                    /* denotes a Java VM                  */
80 _Jv_JNIEnv *_Jv_env;                    /* pointer to native method interface */
81
82
83 /* global variables ***********************************************************/
84
85 s4 vms = 0;                             /* number of VMs created              */
86
87 bool vm_initializing = false;
88 bool vm_exiting = false;
89
90 #if defined(ENABLE_INTRP)
91 u1 *intrp_main_stack = NULL;
92 #endif
93
94 void **stackbottom = NULL;
95
96 char *mainstring = NULL;
97 classinfo *mainclass = NULL;
98
99 char *specificmethodname = NULL;
100 char *specificsignature = NULL;
101
102 bool startit = true;
103
104
105 /* define heap sizes **********************************************************/
106
107 #define HEAP_MAXSIZE      64 * 1024 * 1024  /* default 64MB                   */
108 #define HEAP_STARTSIZE    2  * 1024 * 1024  /* default 2MB                    */
109 #define STACK_SIZE              128 * 1024  /* default 128kB                  */
110
111
112 /* define command line options ************************************************/
113
114 enum {
115         /* Java options */
116
117         OPT_JAR,
118
119         OPT_D32,
120         OPT_D64,
121
122         OPT_CLASSPATH,
123         OPT_D,
124
125         OPT_VERBOSE,
126
127         OPT_VERSION,
128         OPT_SHOWVERSION,
129         OPT_FULLVERSION,
130
131         OPT_HELP,
132         OPT_X,
133
134         /* Java non-standard options */
135
136         OPT_JIT,
137         OPT_INTRP,
138
139         OPT_BOOTCLASSPATH,
140         OPT_BOOTCLASSPATH_A,
141         OPT_BOOTCLASSPATH_P,
142
143         OPT_PROF,
144         OPT_PROF_OPTION,
145
146         OPT_MS,
147         OPT_MX,
148
149         /* CACAO options */
150
151         OPT_VERBOSE1,
152         OPT_NOIEEE,
153         OPT_SOFTNULL,
154         OPT_TIME,
155
156 #if defined(ENABLE_STATISTICS)
157         OPT_STAT,
158 #endif
159
160         OPT_LOG,
161         OPT_CHECK,
162         OPT_LOAD,
163         OPT_METHOD,
164         OPT_SIGNATURE,
165         OPT_SHOW,
166         OPT_ALL,
167
168         OPT_VERBOSETC,
169         OPT_NOVERIFY,
170         OPT_LIBERALUTF,
171         OPT_EAGER,
172
173         /* optimization options */
174
175 #if defined(ENABLE_LOOP)
176         OPT_OLOOP,
177 #endif
178         
179 #if defined(ENABLE_IFCONV)
180         OPT_IFCONV,
181 #endif
182
183 #if defined(ENABLE_LSRA)
184         OPT_LSRA,
185 #endif
186
187 #if defined(ENABLE_INLINING)
188         OPT_INLINING,
189 #endif
190
191 #if defined(ENABLE_INTRP)
192         /* interpreter options */
193
194         OPT_NO_DYNAMIC,
195         OPT_NO_REPLICATION,
196         OPT_NO_QUICKSUPER,
197         OPT_STATIC_SUPERS,
198         OPT_TRACE,
199 #endif
200
201         OPT_SS,
202
203 #ifdef ENABLE_JVMTI
204         OPT_DEBUG,
205         OPT_XRUNJDWP,
206         OPT_NOAGENT,
207         OPT_AGENTLIB,
208         OPT_AGENTPATH,
209 #endif
210
211         DUMMY
212 };
213
214
215 opt_struct opts[] = {
216         /* Java options */
217
218         { "jar",               false, OPT_JAR },
219
220         { "d32",               false, OPT_D32 },
221         { "d64",               false, OPT_D64 },
222         { "client",            false, OPT_IGNORE },
223         { "server",            false, OPT_IGNORE },
224         { "hotspot",           false, OPT_IGNORE },
225
226         { "classpath",         true,  OPT_CLASSPATH },
227         { "cp",                true,  OPT_CLASSPATH },
228         { "D",                 true,  OPT_D },
229         { "version",           false, OPT_VERSION },
230         { "showversion",       false, OPT_SHOWVERSION },
231         { "fullversion",       false, OPT_FULLVERSION },
232         { "help",              false, OPT_HELP },
233         { "?",                 false, OPT_HELP },
234         { "X",                 false, OPT_X },
235
236         { "noasyncgc",         false, OPT_IGNORE },
237         { "noverify",          false, OPT_NOVERIFY },
238         { "liberalutf",        false, OPT_LIBERALUTF },
239         { "v",                 false, OPT_VERBOSE1 },
240         { "verbose:",          true,  OPT_VERBOSE },
241
242 #ifdef TYPECHECK_VERBOSE
243         { "verbosetc",         false, OPT_VERBOSETC },
244 #endif
245 #if defined(__ALPHA__)
246         { "noieee",            false, OPT_NOIEEE },
247 #endif
248         { "softnull",          false, OPT_SOFTNULL },
249         { "time",              false, OPT_TIME },
250 #if defined(ENABLE_STATISTICS)
251         { "stat",              false, OPT_STAT },
252 #endif
253         { "log",               true,  OPT_LOG },
254         { "c",                 true,  OPT_CHECK },
255         { "l",                 false, OPT_LOAD },
256         { "eager",             false, OPT_EAGER },
257         { "sig",               true,  OPT_SIGNATURE },
258         { "all",               false, OPT_ALL },
259 #if defined(ENABLE_LOOP)
260         { "oloop",             false, OPT_OLOOP },
261 #endif
262 #if defined(ENABLE_IFCONV)
263         { "ifconv",            false, OPT_IFCONV },
264 #endif
265 #if defined(ENABLE_LSRA)
266         { "lsra",              false, OPT_LSRA },
267 #endif
268
269 #if defined(ENABLE_INTRP)
270         /* interpreter options */
271
272         { "trace",             false, OPT_TRACE },
273         { "static-supers",     true,  OPT_STATIC_SUPERS },
274         { "no-dynamic",        false, OPT_NO_DYNAMIC },
275         { "no-replication",    false, OPT_NO_REPLICATION },
276         { "no-quicksuper",     false, OPT_NO_QUICKSUPER },
277 #endif
278
279         /* JVMTI Agent Command Line Options */
280 #ifdef ENABLE_JVMTI
281         { "agentlib:",         true,  OPT_AGENTLIB },
282         { "agentpath:",        true,  OPT_AGENTPATH },
283 #endif
284
285         /* Java non-standard options */
286
287         { "Xjit",              false, OPT_JIT },
288         { "Xint",              false, OPT_INTRP },
289         { "Xbootclasspath:",   true,  OPT_BOOTCLASSPATH },
290         { "Xbootclasspath/a:", true,  OPT_BOOTCLASSPATH_A },
291         { "Xbootclasspath/p:", true,  OPT_BOOTCLASSPATH_P },
292 #ifdef ENABLE_JVMTI
293         { "Xdebug",            false, OPT_DEBUG },
294         { "Xnoagent",          false, OPT_NOAGENT },
295         { "Xrunjdwp",          true,  OPT_XRUNJDWP },
296 #endif 
297         { "Xms",               true,  OPT_MS },
298         { "ms",                true,  OPT_MS },
299         { "Xmx",               true,  OPT_MX },
300         { "mx",                true,  OPT_MX },
301         { "Xss",               true,  OPT_SS },
302         { "ss",                true,  OPT_SS },
303         { "Xprof:",            true,  OPT_PROF_OPTION },
304         { "Xprof",             false, OPT_PROF },
305
306         /* keep these at the end of the list */
307
308 #if defined(ENABLE_INLINING)
309         { "i",                 true,  OPT_INLINING },
310 #endif
311         { "m",                 true,  OPT_METHOD },
312         { "s",                 true,  OPT_SHOW },
313
314         { NULL,                false, 0 }
315 };
316
317
318 /* usage ***********************************************************************
319
320    Prints the correct usage syntax to stdout.
321
322 *******************************************************************************/
323
324 void usage(void)
325 {
326         puts("Usage: cacao [-options] classname [arguments]");
327         puts("               (to run a class file)");
328         puts("   or  cacao [-options] -jar jarfile [arguments]");
329         puts("               (to run a standalone jar file)\n");
330
331         puts("Java options:");
332         puts("    -d32                     use 32-bit data model if available");
333         puts("    -d64                     use 64-bit data model if available");
334         puts("    -client                  compatibility (currently ignored)");
335         puts("    -server                  compatibility (currently ignored)");
336         puts("    -hotspot                 compatibility (currently ignored)\n");
337
338         puts("    -cp <path>               specify a path to look for classes");
339         puts("    -classpath <path>        specify a path to look for classes");
340         puts("    -D<name>=<value>         add an entry to the property list");
341         puts("    -verbose[:class|gc|jni]  enable specific verbose output");
342         puts("    -version                 print product version and exit");
343         puts("    -fullversion             print jpackage-compatible product version and exit");
344         puts("    -showversion             print product version and continue");
345         puts("    -help, -?                print this help message");
346         puts("    -X                       print help on non-standard Java options\n");
347
348 #ifdef ENABLE_JVMTI
349         puts("    -agentlib:<agent-lib-name>=<options>  library to load containg JVMTI agent");
350         puts("    -agentpath:<path-to-agent>=<options>  path to library containg JVMTI agent");
351 #endif
352
353         puts("CACAO options:\n");
354         puts("    -v                       write state-information");
355         puts("    -verbose[:call|exception]enable specific verbose output");
356 #ifdef TYPECHECK_VERBOSE
357         puts("    -verbosetc               write debug messages while typechecking");
358 #endif
359 #if defined(__ALPHA__)
360         puts("    -noieee                  don't use ieee compliant arithmetic");
361 #endif
362         puts("    -noverify                don't verify classfiles");
363         puts("    -liberalutf              don't warn about overlong UTF-8 sequences");
364         puts("    -softnull                use software nullpointer check");
365         puts("    -time                    measure the runtime");
366 #if defined(ENABLE_STATISTICS)
367         puts("    -stat                    detailed compiler statistics");
368 #endif
369         puts("    -log logfile             specify a name for the logfile");
370         puts("    -c(heck)b(ounds)         don't check array bounds");
371         puts("            s(ync)           don't check for synchronization");
372 #if defined(ENABLE_LOOP)
373         puts("    -oloop                   optimize array accesses in loops");
374 #endif
375         puts("    -l                       don't start the class after loading");
376         puts("    -eager                   perform eager class loading and linking");
377         puts("    -all                     compile all methods, no execution");
378         puts("    -m                       compile only a specific method");
379         puts("    -sig                     specify signature for a specific method");
380         puts("    -s(how)a(ssembler)       show disassembled listing");
381         puts("           c(onstants)       show the constant pool");
382         puts("           d(atasegment)     show data segment listing");
383         puts("           e(xceptionstubs)  show disassembled exception stubs (only with -sa)");
384         puts("           i(ntermediate)    show intermediate representation");
385         puts("           m(ethods)         show class fields and methods");
386         puts("           n(ative)          show disassembled native stubs");
387         puts("           u(tf)             show the utf - hash");
388 #if defined(ENABLE_INLINING)
389         puts("    -i     n(line)           activate inlining");
390         puts("           v(irtual)         inline virtual methods (uses/turns rt option on)");
391         puts("           e(exception)      inline methods with exceptions");
392         puts("           p(aramopt)        optimize argument renaming");
393         puts("           o(utsiders)       inline methods of foreign classes");
394 #endif /* defined(ENABLE_INLINING) */
395 #if defined(ENABLE_IFCONV)
396         puts("    -ifconv                  use if-conversion");
397 #endif
398 #if defined(ENABLE_LSRA)
399         puts("    -lsra                    use linear scan register allocation");
400 #endif
401
402         /* exit with error code */
403
404         exit(1);
405 }   
406
407
408 static void Xusage(void)
409 {
410 #if defined(ENABLE_JIT)
411         puts("    -Xjit                    JIT mode execution (default)");
412 #endif
413 #if defined(ENABLE_INTRP)
414         puts("    -Xint                    interpreter mode execution");
415 #endif
416         puts("    -Xbootclasspath:<zip/jar files and directories separated by :>");
417     puts("                             value is set as bootstrap class path");
418         puts("    -Xbootclasspath/a:<zip/jar files and directories separated by :>");
419         puts("                             value is appended to the bootstrap class path");
420         puts("    -Xbootclasspath/p:<zip/jar files and directories separated by :>");
421         puts("                             value is prepended to the bootstrap class path");
422         puts("    -Xms<size>               set the initial size of the heap (default: 2MB)");
423         puts("    -Xmx<size>               set the maximum size of the heap (default: 64MB)");
424         puts("    -Xss<size>               set the thread stack size (default: 128kB)");
425         puts("    -Xprof[:bb]              collect and print profiling data");
426 #if defined(ENABLE_JVMTI)
427     /* -Xdebug option depend on gnu classpath JDWP options. options: 
428          transport=dt_socket,address=<hostname:port>,server=(y|n),suspend(y|n) */
429         puts("    -Xdebug           enable remote debugging\n");
430         puts("    -Xrunjdwp transport=[dt_socket|...],address=<hostname:port>,server=[y|n],suspend=[y|n]\n");
431         puts("                      enable remote debugging\n");
432 #endif 
433
434         /* exit with error code */
435
436         exit(1);
437 }   
438
439
440 /* version *********************************************************************
441
442    Only prints cacao version information.
443
444 *******************************************************************************/
445
446 static void version(void)
447 {
448         puts("java version \""JAVA_VERSION"\"");
449         puts("CACAO version "VERSION"");
450
451         puts("Copyright (C) 1996-2005, 2006 R. Grafl, A. Krall, C. Kruegel,");
452         puts("C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring,");
453         puts("E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich,");
454         puts("J. Wenninger, Institut f. Computersprachen - TU Wien\n");
455
456         puts("This program is free software; you can redistribute it and/or");
457         puts("modify it under the terms of the GNU General Public License as");
458         puts("published by the Free Software Foundation; either version 2, or (at");
459         puts("your option) any later version.\n");
460
461         puts("This program is distributed in the hope that it will be useful, but");
462         puts("WITHOUT ANY WARRANTY; without even the implied warranty of");
463         puts("MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU");
464         puts("General Public License for more details.\n");
465
466         puts("Configure/Build options:\n");
467         puts("  ./configure: "VERSION_CONFIGURE_ARGS"");
468 #if defined(__VERSION__)
469         puts("  CC         : "VERSION_CC" ("__VERSION__")");
470 #else
471         puts("  CC         : "VERSION_CC"");
472 #endif
473         puts("  CFLAGS     : "VERSION_CFLAGS"");
474 }
475
476
477 /* fullversion *****************************************************************
478
479    Prints a Sun compatible version information (required e.g. by
480    jpackage, www.jpackage.org).
481
482 *******************************************************************************/
483
484 static void fullversion(void)
485 {
486         puts("java full version \"cacao-"JAVA_VERSION"\"");
487
488         /* exit normally */
489
490         exit(0);
491 }
492
493
494 /* vm_create *******************************************************************
495
496    Creates a JVM.  Called by JNI_CreateJavaVM.
497
498 *******************************************************************************/
499
500 bool vm_create(JavaVMInitArgs *vm_args)
501 {
502         char *cp;
503         s4    cplen;
504         u4    heapmaxsize;
505         u4    heapstartsize;
506         s4    opt;
507         s4    i, j, k;
508
509         /* check the JNI version requested */
510
511         switch (vm_args->version) {
512         case JNI_VERSION_1_1:
513                 break;
514         case JNI_VERSION_1_2:
515         case JNI_VERSION_1_4:
516                 break;
517         default:
518                 return false;
519         }
520
521         /* we only support 1 JVM instance */
522
523         if (vms > 0)
524                 return false;
525
526
527         /* get stuff from the environment *****************************************/
528
529 #if defined(DISABLE_GC)
530         nogc_init(HEAP_MAXSIZE, HEAP_STARTSIZE);
531 #endif
532
533
534         /* set the bootclasspath */
535
536         cp = getenv("BOOTCLASSPATH");
537
538         if (cp) {
539                 bootclasspath = MNEW(char, strlen(cp) + strlen("0"));
540                 strcpy(bootclasspath, cp);
541
542         } else {
543                 cplen = strlen(CACAO_VM_ZIP_PATH) +
544                         strlen(":") +
545                         strlen(CLASSPATH_GLIBJ_ZIP_PATH) +
546                         strlen("0");
547
548                 bootclasspath = MNEW(char, cplen);
549                 strcat(bootclasspath, CACAO_VM_ZIP_PATH);
550                 strcat(bootclasspath, ":");
551                 strcat(bootclasspath, CLASSPATH_GLIBJ_ZIP_PATH);
552         }
553
554
555         /* set the classpath */
556
557         cp = getenv("CLASSPATH");
558
559         if (cp) {
560                 classpath = MNEW(char, strlen(cp) + strlen("0"));
561                 strcat(classpath, cp);
562
563         } else {
564                 classpath = MNEW(char, strlen(".") + strlen("0"));
565                 strcpy(classpath, ".");
566         }
567
568
569         /* interpret the options **************************************************/
570    
571         checknull  = false;
572         opt_noieee = false;
573
574         heapmaxsize   = HEAP_MAXSIZE;
575         heapstartsize = HEAP_STARTSIZE;
576         opt_stacksize = STACK_SIZE;
577
578
579 #if defined(ENABLE_JVMTI)
580         /* initialize JVMTI related  **********************************************/
581         jvmtibrkpt.brk=NULL;
582         jvmtibrkpt.num=0;
583         jvmtibrkpt.size=0;
584         jdwp = jvmti = dbgprocess = false;
585 #endif
586
587         /* initialize properties before commandline handling */
588
589         if (!properties_init())
590                 throw_cacao_exception_exit(string_java_lang_InternalError,
591                                                                    "Unable to init properties");
592
593         /* iterate over all passed options */
594
595         while ((opt = options_get(opts, vm_args)) != OPT_DONE) {
596                 switch (opt) {
597                 case OPT_IGNORE:
598                         break;
599                         
600                 case OPT_JAR:
601                         opt_jar = true;
602                         break;
603
604                 case OPT_D32:
605 #if SIZEOF_VOID_P == 8
606                         puts("Running a 32-bit JVM is not supported on this platform.");
607                         exit(1);
608 #endif
609                         break;
610
611                 case OPT_D64:
612 #if SIZEOF_VOID_P == 4
613                         puts("Running a 64-bit JVM is not supported on this platform.");
614                         exit(1);
615 #endif
616                         break;
617
618                 case OPT_CLASSPATH:
619                         /* forget old classpath and set the argument as new classpath */
620                         MFREE(classpath, char, strlen(classpath));
621
622                         classpath = MNEW(char, strlen(opt_arg) + strlen("0"));
623                         strcpy(classpath, opt_arg);
624                         break;
625
626                 case OPT_D:
627                         for (j = 0; j < strlen(opt_arg); j++) {
628                                 if (opt_arg[j] == '=') {
629                                         opt_arg[j] = '\0';
630                                         properties_add(opt_arg, opt_arg + j + 1);
631                                         goto didit;
632                                 }
633                         }
634
635                         /* if no '=' is given, just create an empty property */
636
637                         properties_add(opt_arg, "");
638                                         
639                 didit:
640                         break;
641
642                 case OPT_BOOTCLASSPATH:
643                         /* Forget default bootclasspath and set the argument as
644                            new boot classpath. */
645                         MFREE(bootclasspath, char, strlen(bootclasspath));
646
647                         bootclasspath = MNEW(char, strlen(opt_arg) + strlen("0"));
648                         strcpy(bootclasspath, opt_arg);
649                         break;
650
651                 case OPT_BOOTCLASSPATH_A:
652                         /* append to end of bootclasspath */
653                         cplen = strlen(bootclasspath);
654
655                         bootclasspath = MREALLOC(bootclasspath,
656                                                                          char,
657                                                                          cplen,
658                                                                          cplen + strlen(":") +
659                                                                          strlen(opt_arg) + strlen("0"));
660
661                         strcat(bootclasspath, ":");
662                         strcat(bootclasspath, opt_arg);
663                         break;
664
665                 case OPT_BOOTCLASSPATH_P:
666                         /* prepend in front of bootclasspath */
667                         cp = bootclasspath;
668                         cplen = strlen(cp);
669
670                         bootclasspath = MNEW(char, strlen(opt_arg) + strlen(":") +
671                                                                  cplen + strlen("0"));
672
673                         strcpy(bootclasspath, opt_arg);
674                         strcat(bootclasspath, ":");
675                         strcat(bootclasspath, cp);
676
677                         MFREE(cp, char, cplen);
678                         break;
679
680 #if defined(ENABLE_JVMTI)
681                 case OPT_DEBUG:
682                         jdwp=true;
683                         break;
684                 case OPT_NOAGENT:
685                         /* I don't know yet what Xnoagent should do. This is only for 
686                            compatiblity with eclipse - motse */
687                         break;
688                 case OPT_XRUNJDWP:
689                         transport = opt_arg;
690                         j=0;
691                         while (transport[j]!='=') j++;
692                         j++;
693                         while (j<strlen(transport)) {
694                                 if (strncmp("suspend=",&transport[j],8)==0) {
695                                         if ((j+8)>=strlen(transport) || 
696                                                 (transport[j+8]!= 'y' && transport[j+8]!= 'n')) {
697                                                 printf("bad Xrunjdwp option: -Xrunjdwp%s\n",transport);
698                                                 usage();
699                                                 break;
700                                         }
701                                         else {
702                                                 suspend = transport[j+8] == 'y';
703                                                 break;
704                                         }
705                                 }
706                                 while (transport[j]!=',') j++;
707                                 j++;
708                         }
709                         
710                         break;
711                 case OPT_AGENTPATH:
712                 case OPT_AGENTLIB:
713                         jvmti=true;
714                         agentarg = opt_arg;
715                         break;
716 #endif
717                         
718                 case OPT_MX:
719                 case OPT_MS:
720                 case OPT_SS:
721                         {
722                                 char c;
723                                 c = opt_arg[strlen(opt_arg) - 1];
724
725                                 if ((c == 'k') || (c == 'K')) {
726                                         j = atoi(opt_arg) * 1024;
727
728                                 } else if ((c == 'm') || (c == 'M')) {
729                                         j = atoi(opt_arg) * 1024 * 1024;
730
731                                 } else
732                                         j = atoi(opt_arg);
733
734                                 if (opt == OPT_MX)
735                                         heapmaxsize = j;
736                                 else if (opt == OPT_MS)
737                                         heapstartsize = j;
738                                 else
739                                         opt_stacksize = j;
740                         }
741                         break;
742
743                 case OPT_VERBOSE1:
744                         opt_verbose = true;
745                         break;
746
747                 case OPT_VERBOSE:
748                         if (strcmp("class", opt_arg) == 0)
749                                 opt_verboseclass = true;
750
751                         else if (strcmp("gc", opt_arg) == 0)
752                                 opt_verbosegc = true;
753
754                         else if (strcmp("jni", opt_arg) == 0)
755                                 opt_verbosejni = true;
756
757                         else if (strcmp("call", opt_arg) == 0)
758                                 opt_verbosecall = true;
759
760                         else if (strcmp("jit", opt_arg) == 0) {
761                                 opt_verbose = true;
762                                 loadverbose = true;
763                                 linkverbose = true;
764                                 initverbose = true;
765                                 compileverbose = true;
766                         }
767                         else if (strcmp("exception", opt_arg) == 0)
768                                 opt_verboseexception = true;
769                         break;
770
771 #ifdef TYPECHECK_VERBOSE
772                 case OPT_VERBOSETC:
773                         typecheckverbose = true;
774                         break;
775 #endif
776                                 
777                 case OPT_VERSION:
778                         version();
779                         exit(0);
780                         break;
781
782                 case OPT_FULLVERSION:
783                         fullversion();
784                         break;
785
786                 case OPT_SHOWVERSION:
787                         version();
788                         break;
789
790                 case OPT_NOIEEE:
791                         opt_noieee = true;
792                         break;
793
794                 case OPT_NOVERIFY:
795                         opt_verify = false;
796                         break;
797
798                 case OPT_LIBERALUTF:
799                         opt_liberalutf = true;
800                         break;
801
802                 case OPT_SOFTNULL:
803                         checknull = true;
804                         break;
805
806                 case OPT_TIME:
807                         getcompilingtime = true;
808                         getloadingtime = true;
809                         break;
810                                         
811 #if defined(ENABLE_STATISTICS)
812                 case OPT_STAT:
813                         opt_stat = true;
814                         break;
815 #endif
816                                         
817                 case OPT_LOG:
818                         log_init(opt_arg);
819                         break;
820                         
821                 case OPT_CHECK:
822                         for (j = 0; j < strlen(opt_arg); j++) {
823                                 switch (opt_arg[j]) {
824                                 case 'b':
825                                         checkbounds = false;
826                                         break;
827                                 case 's':
828                                         checksync = false;
829                                         break;
830                                 default:
831                                         usage();
832                                 }
833                         }
834                         break;
835                         
836                 case OPT_LOAD:
837                         opt_run = false;
838                         makeinitializations = false;
839                         break;
840
841                 case OPT_EAGER:
842                         opt_eager = true;
843                         break;
844
845                 case OPT_METHOD:
846                         opt_run = false;
847                         opt_method = opt_arg;
848                         makeinitializations = false;
849                         break;
850                         
851                 case OPT_SIGNATURE:
852                         opt_signature = opt_arg;
853                         break;
854                         
855                 case OPT_ALL:
856                         compileall = true;
857                         opt_run = false;
858                         makeinitializations = false;
859                         break;
860                         
861                 case OPT_SHOW:       /* Display options */
862                         for (j = 0; j < strlen(opt_arg); j++) {         
863                                 switch (opt_arg[j]) {
864                                 case 'a':
865                                         opt_showdisassemble = true;
866                                         compileverbose = true;
867                                         break;
868                                 case 'c':
869                                         showconstantpool = true;
870                                         break;
871                                 case 'd':
872                                         opt_showddatasegment = true;
873                                         break;
874                                 case 'e':
875                                         opt_showexceptionstubs = true;
876                                         break;
877                                 case 'i':
878                                         opt_showintermediate = true;
879                                         compileverbose = true;
880                                         break;
881                                 case 'm':
882                                         showmethods = true;
883                                         break;
884                                 case 'n':
885                                         opt_shownativestub = true;
886                                         break;
887                                 case 'u':
888                                         showutf = true;
889                                         break;
890                                 default:
891                                         usage();
892                                 }
893                         }
894                         break;
895                         
896 #if defined(ENABLE_LOOP)
897                 case OPT_OLOOP:
898                         opt_loops = true;
899                         break;
900 #endif
901
902 #if defined(ENABLE_INLINING)
903                 case OPT_INLINING:
904                         for (j = 0; j < strlen(opt_arg); j++) {         
905                                 switch (opt_arg[j]) {
906                                 case 'n':
907                                         /* define in options.h; Used in main.c, jit.c
908                                            & inline.c inlining is currently
909                                            deactivated */
910                                         break;
911                                 case 'v':
912                                         inlinevirtuals = true;
913                                         break;
914                                 case 'e':
915                                         inlineexceptions = true;
916                                         break;
917                                 case 'p':
918                                         inlineparamopt = true;
919                                         break;
920                                 case 'o':
921                                         inlineoutsiders = true;
922                                         break;
923                                 default:
924                                         usage();
925                                 }
926                         }
927                         break;
928 #endif /* defined(ENABLE_INLINING) */
929
930 #if defined(ENABLE_IFCONV)
931                 case OPT_IFCONV:
932                         opt_ifconv = true;
933                         break;
934 #endif
935
936 #if defined(ENABLE_LSRA)
937                 case OPT_LSRA:
938                         opt_lsra = true;
939                         break;
940 #endif
941
942                 case OPT_HELP:
943                         usage();
944                         break;
945
946                 case OPT_X:
947                         Xusage();
948                         break;
949
950                 case OPT_PROF_OPTION:
951                         /* use <= to get the last \0 too */
952
953                         for (j = 0, k = 0; j <= strlen(opt_arg); j++) {
954                                 if (opt_arg[j] == ',')
955                                         opt_arg[j] = '\0';
956
957                                 if (opt_arg[j] == '\0') {
958                                         if (strcmp("bb", opt_arg + k) == 0)
959                                                 opt_prof_bb = true;
960
961                                         else {
962                                                 printf("Unknown option: -Xprof:%s\n", opt_arg + k);
963                                                 usage();
964                                         }
965
966                                         /* set k to next char */
967
968                                         k = j + 1;
969                                 }
970                         }
971                         /* fall through */
972
973                 case OPT_PROF:
974                         opt_prof = true;
975                         break;
976
977                 case OPT_JIT:
978 #if defined(ENABLE_JIT)
979                         opt_jit = true;
980 #else
981                         printf("-Xjit option not enabled.\n");
982                         exit(1);
983 #endif
984                         break;
985
986                 case OPT_INTRP:
987 #if defined(ENABLE_INTRP)
988                         opt_intrp = true;
989 #else
990                         printf("-Xint option not enabled.\n");
991                         exit(1);
992 #endif
993                         break;
994
995 #if defined(ENABLE_INTRP)
996                 case OPT_STATIC_SUPERS:
997                         opt_static_supers = atoi(opt_arg);
998                         break;
999
1000                 case OPT_NO_DYNAMIC:
1001                         opt_no_dynamic = true;
1002                         break;
1003
1004                 case OPT_NO_REPLICATION:
1005                         opt_no_replication = true;
1006                         break;
1007
1008                 case OPT_NO_QUICKSUPER:
1009                         opt_no_quicksuper = true;
1010                         break;
1011
1012                 case OPT_TRACE:
1013                         vm_debug = true;
1014                         break;
1015 #endif
1016
1017                 default:
1018                         printf("Unknown option: %s\n",
1019                                    vm_args->options[opt_index].optionString);
1020                         usage();
1021                 }
1022         }
1023
1024
1025         /* get the main class *****************************************************/
1026
1027         if (opt_index < vm_args->nOptions) {
1028                 mainstring = vm_args->options[opt_index++].optionString;
1029
1030                 /* Put the jar file into the classpath (if any). */
1031
1032                 if (opt_jar == true) {
1033                         /* free old classpath */
1034
1035                         MFREE(classpath, char, strlen(classpath));
1036
1037                         /* put jarfile into classpath */
1038
1039                         classpath = MNEW(char, strlen(mainstring) + strlen("0"));
1040
1041                         strcpy(classpath, mainstring);
1042                 
1043                 } else {
1044                         /* replace .'s with /'s in classname */
1045
1046                         for (i = strlen(mainstring) - 1; i >= 0; i--)
1047                                 if (mainstring[i] == '.')
1048                                         mainstring[i] = '/';
1049                 }
1050         }
1051
1052 #if defined(ENABLE_JVMTI)
1053         /* The fork has to occure before threads a created because threads  are 
1054            not forked correctly (see man pthread_atfork). Varibale dbgprocess 
1055            stores information whether this is the debugger or debuggee process. */
1056         if (jvmti || jdwp) {
1057                 set_jvmti_phase(JVMTI_PHASE_ONLOAD);
1058                 dbgprocess = cacaodbgfork();
1059         }
1060
1061         if (dbgprocess && jvmti) { /* is this the parent/debugger process ? */
1062                 agentload(agentarg);
1063                 set_jvmti_phase(JVMTI_PHASE_PRIMORDIAL);
1064         }
1065 #endif
1066
1067
1068         /* initialize this JVM ****************************************************/
1069
1070         vm_initializing = true;
1071
1072         /* initialize the garbage collector */
1073
1074         gc_init(heapmaxsize, heapstartsize);
1075
1076 #if defined(ENABLE_INTRP)
1077         /* Allocate main thread stack on the Java heap. */
1078
1079         if (opt_intrp) {
1080                 intrp_main_stack = GCMNEW(u1, opt_stacksize);
1081                 MSET(intrp_main_stack, 0, u1, opt_stacksize);
1082         }
1083 #endif
1084
1085 #if defined(USE_THREADS)
1086 #if defined(NATIVE_THREADS)
1087         threads_preinit();
1088 #endif
1089         initLocks();
1090 #endif
1091
1092         /* initialize the string hashtable stuff: lock (must be done
1093            _after_ threads_preinit) */
1094
1095         if (!string_init())
1096                 throw_main_exception_exit();
1097
1098         /* initialize the utf8 hashtable stuff: lock, often used utf8
1099            strings (must be done _after_ threads_preinit) */
1100
1101         if (!utf8_init())
1102                 throw_main_exception_exit();
1103
1104         /* initialize the classcache hashtable stuff: lock, hashtable
1105            (must be done _after_ threads_preinit) */
1106
1107         if (!classcache_init())
1108                 throw_main_exception_exit();
1109
1110         /* initialize the loader with bootclasspath (must be done _after_
1111            thread_preinit) */
1112
1113         if (!suck_init())
1114                 throw_main_exception_exit();
1115
1116         suck_add_from_property("java.endorsed.dirs");
1117         suck_add(bootclasspath);
1118
1119         /* initialize the memory subsystem (must be done _after_
1120            threads_preinit) */
1121
1122         if (!memory_init())
1123                 throw_main_exception_exit();
1124
1125         /* initialize the finalizer stuff (must be done _after_
1126            threads_preinit) */
1127
1128         if (!finalizer_init())
1129                 throw_main_exception_exit();
1130
1131         /* install architecture dependent signal handler used for exceptions */
1132
1133         signal_init();
1134
1135         /* initialize the codegen subsystems */
1136
1137         codegen_init();
1138
1139         /* initializes jit compiler */
1140
1141         jit_init();
1142
1143         /* machine dependent initialization */
1144
1145 #if defined(ENABLE_JIT)
1146 # if defined(ENABLE_INTRP)
1147         if (opt_intrp)
1148                 intrp_md_init();
1149         else
1150 # endif
1151                 md_init();
1152 #else
1153         intrp_md_init();
1154 #endif
1155
1156         /* initialize the loader subsystems (must be done _after_
1157        classcache_init) */
1158
1159         if (!loader_init((u1 *) stackbottom))
1160                 throw_main_exception_exit();
1161
1162         if (!linker_init())
1163                 throw_main_exception_exit();
1164
1165         if (!native_init())
1166                 throw_main_exception_exit();
1167
1168         if (!exceptions_init())
1169                 throw_main_exception_exit();
1170
1171         if (!builtin_init())
1172                 throw_main_exception_exit();
1173
1174 #if defined(USE_THREADS)
1175         if (!threads_init((u1 *) stackbottom))
1176                 throw_main_exception_exit();
1177 #endif
1178
1179         /* That's important, otherwise we get into trouble, if the Runtime
1180            static initializer is called before (circular dependency. This
1181            is with classpath 0.09. Another important thing is, that this
1182            has to happen after initThreads!!! */
1183
1184         if (!initialize_class(class_java_lang_System))
1185                 throw_main_exception_exit();
1186
1187         /* JNI init creates a Java object (this means running Java code) */
1188
1189         if (!jni_init())
1190                 throw_main_exception_exit();
1191
1192 #if defined(ENABLE_PROFILING)
1193         /* initialize profiling */
1194
1195         if (!profile_init())
1196                 throw_main_exception_exit();
1197 #endif
1198
1199 #if defined(USE_THREADS)
1200         /* finally, start the finalizer thread */
1201
1202         if (!finalizer_start_thread())
1203                 throw_main_exception_exit();
1204
1205         /* start the profile sampling thread */
1206
1207 /*      if (!profile_start_thread()) */
1208 /*              throw_main_exception_exit(); */
1209 #endif
1210
1211         /* increment the number of VMs */
1212
1213         vms++;
1214
1215         /* initialization is done */
1216
1217         vm_initializing = false;
1218
1219         /* everything's ok */
1220
1221         return true;
1222 }
1223
1224
1225 /* vm_destroy ******************************************************************
1226
1227    Unloads a Java VM and reclaims its resources.
1228
1229 *******************************************************************************/
1230
1231 s4 vm_destroy(JavaVM *vm)
1232 {
1233 #if defined(USE_THREADS)
1234 #if defined(NATIVE_THREADS)
1235         joinAllThreads();
1236 #else
1237         killThread(currentThread);
1238 #endif
1239 #endif
1240
1241         /* everything's ok */
1242
1243         return 0;
1244 }
1245
1246
1247 /* vm_exit *********************************************************************
1248
1249    Calls java.lang.System.exit(I)V to exit the JavaVM correctly.
1250
1251 *******************************************************************************/
1252
1253 void vm_exit(s4 status)
1254 {
1255         methodinfo *m;
1256
1257         /* signal that we are exiting */
1258
1259         vm_exiting = true;
1260
1261         assert(class_java_lang_System);
1262         assert(class_java_lang_System->state & CLASS_LOADED);
1263
1264 #if defined(ENABLE_JVMTI)
1265         if (dbgprocess) {
1266                 set_jvmti_phase(JVMTI_PHASE_DEAD);
1267                 if (jvmti) agentunload();
1268         }
1269 #endif
1270
1271         if (!link_class(class_java_lang_System))
1272                 throw_main_exception_exit();
1273
1274         /* call java.lang.System.exit(I)V */
1275
1276         m = class_resolveclassmethod(class_java_lang_System,
1277                                                                  utf_new_char("exit"),
1278                                                                  utf_int__void,
1279                                                                  class_java_lang_Object,
1280                                                                  true);
1281         
1282         if (m == NULL)
1283                 throw_main_exception_exit();
1284
1285         /* call the exit function with passed exit status */
1286
1287         (void) vm_call_method(m, NULL, status);
1288
1289         /* If we had an exception, just ignore the exception and exit with
1290            the proper code. */
1291
1292         vm_shutdown(status);
1293 }
1294
1295
1296 /* vm_shutdown *****************************************************************
1297
1298    Terminates the system immediately without freeing memory explicitly
1299    (to be used only for abnormal termination).
1300         
1301 *******************************************************************************/
1302
1303 void vm_shutdown(s4 status)
1304 {
1305 #if defined(ENABLE_JVMTI)
1306         if (dbgprocess) {
1307                 set_jvmti_phase(JVMTI_PHASE_DEAD);
1308                 if (jvmti) agentunload();
1309                 ipcrm();
1310         }
1311 #endif
1312         if (opt_verbose || getcompilingtime || opt_stat) {
1313                 log_text("CACAO terminated by shutdown");
1314                 dolog("Exit status: %d\n", (s4) status);
1315         }
1316
1317         exit(status);
1318 }
1319
1320
1321 /* vm_exit_handler *************************************************************
1322
1323    The exit_handler function is called upon program termination.
1324
1325    ATTENTION: Don't free system resources here! Some threads may still
1326    be running as this is called from VMRuntime.exit(). The OS does the
1327    cleanup for us.
1328
1329 *******************************************************************************/
1330
1331 void vm_exit_handler(void)
1332 {
1333 #if defined(ENABLE_JVMTI)
1334         if (jvmti && jdwp) set_jvmti_phase(JVMTI_PHASE_DEAD);
1335         if (jvmti) agentunload();
1336         ipcrm();
1337 #endif
1338
1339 #if !defined(NDEBUG)
1340         if (showmethods)
1341                 class_showmethods(mainclass);
1342
1343         if (showconstantpool)
1344                 class_showconstantpool(mainclass);
1345
1346         if (showutf)
1347                 utf_show();
1348
1349 # if defined(ENABLE_PROFILING)
1350         if (opt_prof)
1351                 profile_printstats();
1352 # endif
1353 #endif
1354
1355 #if defined(USE_THREADS) && !defined(NATIVE_THREADS)
1356         clear_thread_flags();           /* restores standard file descriptor
1357                                        flags */
1358 #endif
1359
1360 #if defined(ENABLE_RT_TIMING)
1361         rt_timing_print_time_stats(stderr);
1362 #endif
1363
1364 #if defined(ENABLE_CYCLES_STATS)
1365         builtin_print_cycles_stats(stderr);
1366         stacktrace_print_cycles_stats(stderr);
1367 #endif
1368
1369         if (opt_verbose || getcompilingtime || opt_stat) {
1370                 log_text("CACAO terminated");
1371
1372 #if defined(ENABLE_STATISTICS)
1373                 if (opt_stat) {
1374                         print_stats();
1375 #ifdef TYPECHECK_STATISTICS
1376                         typecheck_print_statistics(get_logfile());
1377 #endif
1378                 }
1379
1380                 mem_usagelog(1);
1381
1382                 if (getcompilingtime)
1383                         print_times();
1384 #endif
1385         }
1386         /* vm_print_profile(stderr);*/
1387 }
1388
1389
1390 /* vm_vmargs_from_valist *******************************************************
1391
1392    XXX
1393
1394 *******************************************************************************/
1395
1396 static void vm_vmargs_from_valist(methodinfo *m, java_objectheader *o,
1397                                                                   vm_arg *vmargs, va_list ap)
1398 {
1399         typedesc *paramtypes;
1400         s4        i;
1401
1402         paramtypes = m->parseddesc->paramtypes;
1403
1404         /* if method is non-static fill first block and skip `this' pointer */
1405
1406         i = 0;
1407
1408         if (o != NULL) {
1409                 /* the `this' pointer */
1410                 vmargs[0].type = TYPE_ADR;
1411                 vmargs[0].data = (u8) (ptrint) o;
1412
1413                 paramtypes++;
1414                 i++;
1415         } 
1416
1417         for (; i < m->parseddesc->paramcount; i++, paramtypes++) {
1418                 switch (paramtypes->decltype) {
1419                 /* primitive types */
1420                 case PRIMITIVETYPE_BOOLEAN: 
1421                 case PRIMITIVETYPE_BYTE:
1422                 case PRIMITIVETYPE_CHAR:
1423                 case PRIMITIVETYPE_SHORT: 
1424                 case PRIMITIVETYPE_INT:
1425                         vmargs[i].type = TYPE_INT;
1426                         vmargs[i].data = (s8) va_arg(ap, s4);
1427                         break;
1428
1429                 case PRIMITIVETYPE_LONG:
1430                         vmargs[i].type = TYPE_LNG;
1431                         vmargs[i].data = (s8) va_arg(ap, s8);
1432                         break;
1433
1434                 case PRIMITIVETYPE_FLOAT:
1435                         vmargs[i].type = TYPE_FLT;
1436 #if defined(__ALPHA__)
1437                         /* this keeps the assembler function much simpler */
1438
1439                         *((jdouble *) (&vmargs[i].data)) = (jdouble) va_arg(ap, jdouble);
1440 #else
1441                         *((jfloat *) (&vmargs[i].data)) = (jfloat) va_arg(ap, jdouble);
1442 #endif
1443                         break;
1444
1445                 case PRIMITIVETYPE_DOUBLE:
1446                         vmargs[i].type = TYPE_DBL;
1447                         *((jdouble *) (&vmargs[i].data)) = (jdouble) va_arg(ap, jdouble);
1448                         break;
1449
1450                 case TYPE_ADR: 
1451                         vmargs[i].type = TYPE_ADR;
1452                         vmargs[i].data = (u8) (ptrint) va_arg(ap, void*);
1453                         break;
1454                 }
1455         }
1456 }
1457
1458
1459 /* vm_vmargs_from_jvalue *******************************************************
1460
1461    XXX
1462
1463 *******************************************************************************/
1464
1465 static void vm_vmargs_from_jvalue(methodinfo *m, java_objectheader *o,
1466                                                                   vm_arg *vmargs, jvalue *args)
1467 {
1468         typedesc *paramtypes;
1469         s4        i;
1470         s4        j;
1471
1472         paramtypes = m->parseddesc->paramtypes;
1473
1474         /* if method is non-static fill first block and skip `this' pointer */
1475
1476         i = 0;
1477
1478         if (o != NULL) {
1479                 /* the `this' pointer */
1480                 vmargs[0].type = TYPE_ADR;
1481                 vmargs[0].data = (u8) (ptrint) o;
1482
1483                 paramtypes++;
1484                 i++;
1485         } 
1486
1487         for (j = 0; i < m->parseddesc->paramcount; i++, j++, paramtypes++) {
1488                 switch (paramtypes->decltype) {
1489                 /* primitive types */
1490                 case PRIMITIVETYPE_BOOLEAN: 
1491                 case PRIMITIVETYPE_BYTE:
1492                 case PRIMITIVETYPE_CHAR:
1493                 case PRIMITIVETYPE_SHORT: 
1494                 case PRIMITIVETYPE_INT:
1495                         vmargs[i].type = TYPE_INT;
1496                         vmargs[i].data = (s8) args[j].i;
1497                         break;
1498
1499                 case PRIMITIVETYPE_LONG:
1500                         vmargs[i].type = TYPE_LNG;
1501                         vmargs[i].data = (s8) args[j].j;
1502                         break;
1503
1504                 case PRIMITIVETYPE_FLOAT:
1505                         vmargs[i].type = TYPE_FLT;
1506 #if defined(__ALPHA__)
1507                         /* this keeps the assembler function much simpler */
1508
1509                         *((jdouble *) (&vmargs[i].data)) = (jdouble) args[j].f;
1510 #else
1511                         *((jfloat *) (&vmargs[i].data)) = args[j].f;
1512 #endif
1513                         break;
1514
1515                 case PRIMITIVETYPE_DOUBLE:
1516                         vmargs[i].type = TYPE_DBL;
1517                         *((jdouble *) (&vmargs[i].data)) = args[j].d;
1518                         break;
1519
1520                 case TYPE_ADR: 
1521                         vmargs[i].type = TYPE_ADR;
1522                         vmargs[i].data = (u8) (ptrint) args[j].l;
1523                         break;
1524                 }
1525         }
1526 }
1527
1528
1529 /* vm_call_method **************************************************************
1530
1531    Calls a Java method with a variable number of arguments and returns
1532    an address.
1533
1534 *******************************************************************************/
1535
1536 java_objectheader *vm_call_method(methodinfo *m, java_objectheader *o, ...)
1537 {
1538         va_list            ap;
1539         java_objectheader *ro;
1540
1541         va_start(ap, o);
1542         ro = vm_call_method_valist(m, o, ap);
1543         va_end(ap);
1544
1545         return ro;
1546 }
1547
1548
1549 /* vm_call_method_valist *******************************************************
1550
1551    Calls a Java method with a variable number of arguments, passed via
1552    a va_list, and returns an address.
1553
1554 *******************************************************************************/
1555
1556 java_objectheader *vm_call_method_valist(methodinfo *m, java_objectheader *o,
1557                                                                                  va_list ap)
1558 {
1559         s4                 vmargscount;
1560         vm_arg            *vmargs;
1561         java_objectheader *ro;
1562         s4                 dumpsize;
1563
1564         /* mark start of dump memory area */
1565
1566         dumpsize = dump_size();
1567
1568         /* get number of Java method arguments */
1569
1570         vmargscount = m->parseddesc->paramcount;
1571
1572         /* allocate vm_arg array */
1573
1574         vmargs = DMNEW(vm_arg, vmargscount);
1575
1576         /* fill the vm_arg array from a va_list */
1577
1578         vm_vmargs_from_valist(m, o, vmargs, ap);
1579
1580         /* call the Java method */
1581
1582         ro = vm_call_method_vmarg(m, vmargscount, vmargs);
1583
1584         /* release dump area */
1585
1586         dump_release(dumpsize);
1587
1588         return ro;
1589 }
1590
1591
1592 /* vm_call_method_jvalue *******************************************************
1593
1594    Calls a Java method with a variable number of arguments, passed via
1595    a jvalue array, and returns an address.
1596
1597 *******************************************************************************/
1598
1599 java_objectheader *vm_call_method_jvalue(methodinfo *m, java_objectheader *o,
1600                                                                                  jvalue *args)
1601 {
1602         s4                 vmargscount;
1603         vm_arg            *vmargs;
1604         java_objectheader *ro;
1605         s4                 dumpsize;
1606
1607         /* mark start of dump memory area */
1608
1609         dumpsize = dump_size();
1610
1611         /* get number of Java method arguments */
1612
1613         vmargscount = m->parseddesc->paramcount;
1614
1615         /* allocate vm_arg array */
1616
1617         vmargs = DMNEW(vm_arg, vmargscount);
1618
1619         /* fill the vm_arg array from a va_list */
1620
1621         vm_vmargs_from_jvalue(m, o, vmargs, args);
1622
1623         /* call the Java method */
1624
1625         ro = vm_call_method_vmarg(m, vmargscount, vmargs);
1626
1627         /* release dump area */
1628
1629         dump_release(dumpsize);
1630
1631         return ro;
1632 }
1633
1634
1635 /* vm_call_method_vmarg ********************************************************
1636
1637    Calls a Java method with a variable number of arguments, passed via
1638    a vm_arg array, and returns an address.
1639
1640 *******************************************************************************/
1641
1642 java_objectheader *vm_call_method_vmarg(methodinfo *m, s4 vmargscount,
1643                                                                                 vm_arg *vmargs)
1644 {
1645         java_objectheader *o;
1646
1647 #if defined(ENABLE_JIT)
1648 # if defined(ENABLE_INTRP)
1649         if (opt_intrp)
1650                 o = intrp_asm_vm_call_method(m, vmargscount, vmargs);
1651         else
1652 # endif
1653                 o = asm_vm_call_method(m, vmargscount, vmargs);
1654 #else
1655         o = intrp_asm_vm_call_method(m, vmargscount, vmargs);
1656 #endif
1657
1658         return o;
1659 }
1660
1661
1662 /* vm_call_method_int **********************************************************
1663
1664    Calls a Java method with a variable number of arguments and returns
1665    an integer (s4).
1666
1667 *******************************************************************************/
1668
1669 s4 vm_call_method_int(methodinfo *m, java_objectheader *o, ...)
1670 {
1671         va_list ap;
1672         s4      i;
1673
1674         va_start(ap, o);
1675         i = vm_call_method_int_valist(m, o, ap);
1676         va_end(ap);
1677
1678         return i;
1679 }
1680
1681
1682 /* vm_call_method_int_valist ***************************************************
1683
1684    Calls a Java method with a variable number of arguments, passed via
1685    a va_list, and returns an integer (s4).
1686
1687 *******************************************************************************/
1688
1689 s4 vm_call_method_int_valist(methodinfo *m, java_objectheader *o, va_list ap)
1690 {
1691         s4      vmargscount;
1692         vm_arg *vmargs;
1693         s4      i;
1694         s4      dumpsize;
1695
1696         /* mark start of dump memory area */
1697
1698         dumpsize = dump_size();
1699
1700         /* get number of Java method arguments */
1701
1702         vmargscount = m->parseddesc->paramcount;
1703
1704         /* allocate vm_arg array */
1705
1706         vmargs = DMNEW(vm_arg, vmargscount);
1707
1708         /* fill the vm_arg array from a va_list */
1709
1710         vm_vmargs_from_valist(m, o, vmargs, ap);
1711
1712         /* call the Java method */
1713
1714         i = vm_call_method_int_vmarg(m, vmargscount, vmargs);
1715
1716         /* release dump area */
1717
1718         dump_release(dumpsize);
1719
1720         return i;
1721 }
1722
1723
1724 /* vm_call_method_int_jvalue ***************************************************
1725
1726    Calls a Java method with a variable number of arguments, passed via
1727    a jvalue array, and returns an integer (s4).
1728
1729 *******************************************************************************/
1730
1731 s4 vm_call_method_int_jvalue(methodinfo *m, java_objectheader *o, jvalue *args)
1732 {
1733         s4      vmargscount;
1734         vm_arg *vmargs;
1735         s4      i;
1736         s4      dumpsize;
1737
1738         /* mark start of dump memory area */
1739
1740         dumpsize = dump_size();
1741
1742         /* get number of Java method arguments */
1743
1744         vmargscount = m->parseddesc->paramcount;
1745
1746         /* allocate vm_arg array */
1747
1748         vmargs = DMNEW(vm_arg, vmargscount);
1749
1750         /* fill the vm_arg array from a va_list */
1751
1752         vm_vmargs_from_jvalue(m, o, vmargs, args);
1753
1754         /* call the Java method */
1755
1756         i = vm_call_method_int_vmarg(m, vmargscount, vmargs);
1757
1758         /* release dump area */
1759
1760         dump_release(dumpsize);
1761
1762         return i;
1763 }
1764
1765
1766 /* vm_call_method_int_vmarg ****************************************************
1767
1768    Calls a Java method with a variable number of arguments, passed via
1769    a vm_arg array, and returns an integer (s4).
1770
1771 *******************************************************************************/
1772
1773 s4 vm_call_method_int_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
1774 {
1775         s4 i;
1776
1777 #if defined(ENABLE_JIT)
1778 # if defined(ENABLE_INTRP)
1779         if (opt_intrp)
1780                 i = intrp_asm_vm_call_method_int(m, vmargscount, vmargs);
1781         else
1782 # endif
1783                 i = asm_vm_call_method_int(m, vmargscount, vmargs);
1784 #else
1785         i = intrp_asm_vm_call_method_int(m, vmargscount, vmargs);
1786 #endif
1787
1788         return i;
1789 }
1790
1791
1792 /* vm_call_method_long *********************************************************
1793
1794    Calls a Java method with a variable number of arguments and returns
1795    a long (s8).
1796
1797 *******************************************************************************/
1798
1799 s8 vm_call_method_long(methodinfo *m, java_objectheader *o, ...)
1800 {
1801         va_list ap;
1802         s8      l;
1803
1804         va_start(ap, o);
1805         l = vm_call_method_long_valist(m, o, ap);
1806         va_end(ap);
1807
1808         return l;
1809 }
1810
1811
1812 /* vm_call_method_long_valist **************************************************
1813
1814    Calls a Java method with a variable number of arguments, passed via
1815    a va_list, and returns a long (s8).
1816
1817 *******************************************************************************/
1818
1819 s8 vm_call_method_long_valist(methodinfo *m, java_objectheader *o, va_list ap)
1820 {
1821         s4      vmargscount;
1822         vm_arg *vmargs;
1823         s8      l;
1824         s4      dumpsize;
1825
1826         /* mark start of dump memory area */
1827
1828         dumpsize = dump_size();
1829
1830         /* get number of Java method arguments */
1831
1832         vmargscount = m->parseddesc->paramcount;
1833
1834         /* allocate vm_arg array */
1835
1836         vmargs = DMNEW(vm_arg, vmargscount);
1837
1838         /* fill the vm_arg array from a va_list */
1839
1840         vm_vmargs_from_valist(m, o, vmargs, ap);
1841
1842         /* call the Java method */
1843
1844         l = vm_call_method_long_vmarg(m, vmargscount, vmargs);
1845
1846         /* release dump area */
1847
1848         dump_release(dumpsize);
1849
1850         return l;
1851 }
1852
1853
1854 /* vm_call_method_long_jvalue **************************************************
1855
1856    Calls a Java method with a variable number of arguments, passed via
1857    a jvalue array, and returns a long (s8).
1858
1859 *******************************************************************************/
1860
1861 s8 vm_call_method_long_jvalue(methodinfo *m, java_objectheader *o, jvalue *args)
1862 {
1863         s4      vmargscount;
1864         vm_arg *vmargs;
1865         s8      l;
1866         s4      dumpsize;
1867
1868         /* mark start of dump memory area */
1869
1870         dumpsize = dump_size();
1871
1872         /* get number of Java method arguments */
1873
1874         vmargscount = m->parseddesc->paramcount;
1875
1876         /* allocate vm_arg array */
1877
1878         vmargs = DMNEW(vm_arg, vmargscount);
1879
1880         /* fill the vm_arg array from a va_list */
1881
1882         vm_vmargs_from_jvalue(m, o, vmargs, args);
1883
1884         /* call the Java method */
1885
1886         l = vm_call_method_long_vmarg(m, vmargscount, vmargs);
1887
1888         /* release dump area */
1889
1890         dump_release(dumpsize);
1891
1892         return l;
1893 }
1894
1895
1896 /* vm_call_method_long_vmarg ***************************************************
1897
1898    Calls a Java method with a variable number of arguments, passed via
1899    a vm_arg array, and returns a long (s8).
1900
1901 *******************************************************************************/
1902
1903 s8 vm_call_method_long_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
1904 {
1905         s8 l;
1906
1907 #if defined(ENABLE_JIT)
1908 # if defined(ENABLE_INTRP)
1909         if (opt_intrp)
1910                 l = intrp_asm_vm_call_method_long(m, vmargscount, vmargs);
1911         else
1912 # endif
1913                 l = asm_vm_call_method_long(m, vmargscount, vmargs);
1914 #else
1915         l = intrp_asm_vm_call_method_long(m, vmargscount, vmargs);
1916 #endif
1917
1918         return l;
1919 }
1920
1921
1922 /* vm_call_method_float ********************************************************
1923
1924    Calls a Java method with a variable number of arguments and returns
1925    an float.
1926
1927 *******************************************************************************/
1928
1929 float vm_call_method_float(methodinfo *m, java_objectheader *o, ...)
1930 {
1931         va_list ap;
1932         float   f;
1933
1934         va_start(ap, o);
1935         f = vm_call_method_float_valist(m, o, ap);
1936         va_end(ap);
1937
1938         return f;
1939 }
1940
1941
1942 /* vm_call_method_float_valist *************************************************
1943
1944    Calls a Java method with a variable number of arguments, passed via
1945    a va_list, and returns a float.
1946
1947 *******************************************************************************/
1948
1949 float vm_call_method_float_valist(methodinfo *m, java_objectheader *o,
1950                                                                   va_list ap)
1951 {
1952         s4      vmargscount;
1953         vm_arg *vmargs;
1954         float   f;
1955         s4      dumpsize;
1956
1957         /* mark start of dump memory area */
1958
1959         dumpsize = dump_size();
1960
1961         /* get number of Java method arguments */
1962
1963         vmargscount = m->parseddesc->paramcount;
1964
1965         /* allocate vm_arg array */
1966
1967         vmargs = DMNEW(vm_arg, vmargscount);
1968
1969         /* fill the vm_arg array from a va_list */
1970
1971         vm_vmargs_from_valist(m, o, vmargs, ap);
1972
1973         /* call the Java method */
1974
1975         f = vm_call_method_float_vmarg(m, vmargscount, vmargs);
1976
1977         /* release dump area */
1978
1979         dump_release(dumpsize);
1980
1981         return f;
1982 }
1983
1984
1985 /* vm_call_method_float_jvalue *************************************************
1986
1987    Calls a Java method with a variable number of arguments, passed via
1988    a jvalue array, and returns a float.
1989
1990 *******************************************************************************/
1991
1992 float vm_call_method_float_jvalue(methodinfo *m, java_objectheader *o,
1993                                                                   jvalue *args)
1994 {
1995         s4      vmargscount;
1996         vm_arg *vmargs;
1997         float   f;
1998         s4      dumpsize;
1999
2000         /* mark start of dump memory area */
2001
2002         dumpsize = dump_size();
2003
2004         /* get number of Java method arguments */
2005
2006         vmargscount = m->parseddesc->paramcount;
2007
2008         /* allocate vm_arg array */
2009
2010         vmargs = DMNEW(vm_arg, vmargscount);
2011
2012         /* fill the vm_arg array from a va_list */
2013
2014         vm_vmargs_from_jvalue(m, o, vmargs, args);
2015
2016         /* call the Java method */
2017
2018         f = vm_call_method_float_vmarg(m, vmargscount, vmargs);
2019
2020         /* release dump area */
2021
2022         dump_release(dumpsize);
2023
2024         return f;
2025 }
2026
2027
2028 /* vm_call_method_float_vmarg **************************************************
2029
2030    Calls a Java method with a variable number of arguments and returns
2031    an float.
2032
2033 *******************************************************************************/
2034
2035 float vm_call_method_float_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
2036 {
2037         float f;
2038
2039 #if defined(ENABLE_JIT)
2040 # if defined(ENABLE_INTRP)
2041         if (opt_intrp)
2042                 f = intrp_asm_vm_call_method_float(m, vmargscount, vmargs);
2043         else
2044 # endif
2045                 f = asm_vm_call_method_float(m, vmargscount, vmargs);
2046 #else
2047         f = intrp_asm_vm_call_method_float(m, vmargscount, vmargs);
2048 #endif
2049
2050         return f;
2051 }
2052
2053
2054 /* vm_call_method_double *******************************************************
2055
2056    Calls a Java method with a variable number of arguments and returns
2057    a double.
2058
2059 *******************************************************************************/
2060
2061 double vm_call_method_double(methodinfo *m, java_objectheader *o, ...)
2062 {
2063         va_list ap;
2064         double  d;
2065
2066         va_start(ap, o);
2067         d = vm_call_method_double_valist(m, o, ap);
2068         va_end(ap);
2069
2070         return d;
2071 }
2072
2073
2074 /* vm_call_method_double_valist ************************************************
2075
2076    Calls a Java method with a variable number of arguments, passed via
2077    a va_list, and returns a double.
2078
2079 *******************************************************************************/
2080
2081 double vm_call_method_double_valist(methodinfo *m, java_objectheader *o,
2082                                                                         va_list ap)
2083 {
2084         s4      vmargscount;
2085         vm_arg *vmargs;
2086         double  d;
2087         s4      dumpsize;
2088
2089         /* mark start of dump memory area */
2090
2091         dumpsize = dump_size();
2092
2093         /* get number of Java method arguments */
2094
2095         vmargscount = m->parseddesc->paramcount;
2096
2097         /* allocate vm_arg array */
2098
2099         vmargs = DMNEW(vm_arg, vmargscount);
2100
2101         /* fill the vm_arg array from a va_list */
2102
2103         vm_vmargs_from_valist(m, o, vmargs, ap);
2104
2105         /* call the Java method */
2106
2107         d = vm_call_method_double_vmarg(m, vmargscount, vmargs);
2108
2109         /* release dump area */
2110
2111         dump_release(dumpsize);
2112
2113         return d;
2114 }
2115
2116
2117 /* vm_call_method_double_jvalue ************************************************
2118
2119    Calls a Java method with a variable number of arguments, passed via
2120    a jvalue array, and returns a double.
2121
2122 *******************************************************************************/
2123
2124 double vm_call_method_double_jvalue(methodinfo *m, java_objectheader *o,
2125                                                                         jvalue *args)
2126 {
2127         s4      vmargscount;
2128         vm_arg *vmargs;
2129         double  d;
2130         s4      dumpsize;
2131
2132         /* mark start of dump memory area */
2133
2134         dumpsize = dump_size();
2135
2136         /* get number of Java method arguments */
2137
2138         vmargscount = m->parseddesc->paramcount;
2139
2140         /* allocate vm_arg array */
2141
2142         vmargs = DMNEW(vm_arg, vmargscount);
2143
2144         /* fill the vm_arg array from a va_list */
2145
2146         vm_vmargs_from_jvalue(m, o, vmargs, args);
2147
2148         /* call the Java method */
2149
2150         d = vm_call_method_double_vmarg(m, vmargscount, vmargs);
2151
2152         /* release dump area */
2153
2154         dump_release(dumpsize);
2155
2156         return d;
2157 }
2158
2159
2160 /* vm_call_method_double_vmarg *************************************************
2161
2162    Calls a Java method with a variable number of arguments and returns
2163    a double.
2164
2165 *******************************************************************************/
2166
2167 double vm_call_method_double_vmarg(methodinfo *m, s4 vmargscount,
2168                                                                    vm_arg *vmargs)
2169 {
2170         double d;
2171
2172 #if defined(ENABLE_JIT)
2173 # if defined(ENABLE_INTRP)
2174         if (opt_intrp)
2175                 d = intrp_asm_vm_call_method_double(m, vmargscount, vmargs);
2176         else
2177 # endif
2178                 d = asm_vm_call_method_double(m, vmargscount, vmargs);
2179 #else
2180         d = intrp_asm_vm_call_method_double(m, vmargscount, vmargs);
2181 #endif
2182
2183         return d;
2184 }
2185
2186
2187 /*
2188  * These are local overrides for various environment variables in Emacs.
2189  * Please do not remove this and leave it at the end of the file, where
2190  * Emacs will automagically detect them.
2191  * ---------------------------------------------------------------------
2192  * Local variables:
2193  * mode: c
2194  * indent-tabs-mode: t
2195  * c-basic-offset: 4
2196  * tab-width: 4
2197  * End:
2198  */