Edwin Steiner
Christian Thalinger
- $Id: loader.c 1183 2004-06-19 12:20:06Z twisti $
+ $Id: loader.c 1329 2004-07-21 15:36:33Z twisti $
*/
#include <string.h>
#include <assert.h>
#include <sys/stat.h>
+#include "exceptions.h"
#include "global.h"
#include "loader.h"
-#include "main.h"
+#include "options.h"
#include "native.h"
#include "tables.h"
#include "builtin.h"
#include "jit/jit.h"
#include "asmpart.h"
+#include "options.h"
+#include "statistics.h"
#include "toolbox/memory.h"
#include "toolbox/logging.h"
#include "threads/thread.h"
/* global variables ***********************************************************/
-int count_class_infos = 0; /* variables for measurements */
-int count_const_pool_len = 0;
-int count_vftbl_len = 0;
-int count_all_methods = 0;
-int count_vmcode_len = 0;
-int count_extable_len = 0;
-int count_class_loads = 0;
-int count_class_inits = 0;
-
static s4 interfaceindex; /* sequential numbering of interfaces */
static s4 classvalue;
classinfo *pseudo_class_Arraystub = NULL;
classinfo *pseudo_class_Null = NULL;
classinfo *pseudo_class_New = NULL;
-vftbl *pseudo_class_Arraystub_vftbl = NULL;
+vftbl_t *pseudo_class_Arraystub_vftbl = NULL;
utf *array_packagename = NULL;
static char *classpath = ""; /* searchpath for classfiles */
-static java_objectheader *new_classformaterror(classinfo *c, char *message, ...)
-{
- char cfmessage[MAXLOGTEXT];
- va_list ap;
-
- utf_sprint_classname(cfmessage, c->name);
- sprintf(cfmessage + strlen(cfmessage), " (");
-
- va_start(ap, message);
- vsprintf(cfmessage + strlen(cfmessage), message, ap);
- va_end(ap);
-
- sprintf(cfmessage + strlen(cfmessage), ")");
-
- return new_exception_message(string_java_lang_ClassFormatError, cfmessage);
-}
-
-
/* check_classbuffer_size ******************************************************
assert that at least <len> bytes are left to read
isZip = 0;
filenamelen = end - start;
- if (filenamelen>3) {
+ if (filenamelen > 3) {
if (strncasecmp(end - 3, "zip", 3) == 0 ||
strncasecmp(end - 3, "jar", 3) == 0) {
isZip = 1;
strncpy(filename, start, filenamelen);
filename[filenamelen + 1] = '\0';
- tmp = 0;
+ tmp = NULL;
if (isZip) {
-#ifdef USE_ZLIB
+#if defined(USE_ZLIB)
unzFile uf = unzOpen(filename);
if (uf) {
tmp = (union classpath_info *) NEW(classpath_info);
tmp->archive.type = CLASSPATH_ARCHIVE;
tmp->archive.uf = uf;
- tmp->archive.next = 0;
- filename = 0;
+ tmp->archive.next = NULL;
+ filename = NULL;
}
#else
- panic("Zip/JAR not supported");
+ throw_cacao_exception_exit(string_java_lang_InternalError, "zip/jar files not supported");
#endif
} else {
tmp->filepath.filename = filename;
tmp->filepath.pathlen = filenamelen;
- filename = 0;
+ filename = NULL;
}
if (tmp) {
filenamelen += 6;
for (currPos = classpath_entries; currPos != 0; currPos = currPos->filepath.next) {
-#ifdef USE_ZLIB
+#if defined(USE_ZLIB)
if (currPos->filepath.type == CLASSPATH_ARCHIVE) {
if (cacao_locate(currPos->archive.uf, c->name) == UNZ_OK) {
unz_file_info file_info;
return cb;
}
}
-#ifdef USE_ZLIB
+#if defined(USE_ZLIB)
}
#endif
}
}
m->jcode = NULL;
+ m->basicblockcount = 0;
+ m->basicblocks = NULL;
+ m->basicblockindex = NULL;
+ m->instructioncount = 0;
+ m->instructions = NULL;
+ m->stackcount = 0;
+ m->stack = NULL;
m->exceptiontable = NULL;
- m->entrypoint = NULL;
- m->mcode = NULL;
+ m->registerdata = NULL;
m->stubroutine = NULL;
+ m->mcode = NULL;
+ m->entrypoint = NULL;
m->methodUsed = NOTUSED;
m->monoPoly = MONO;
m->subRedefs = 0;
m->jcodelength = suck_u4(cb);
- if (m->jcodelength == 0)
- panic("bytecode has zero length");
+ if (m->jcodelength == 0) {
+ *exceptionptr =
+ new_classformaterror(c, "Code of a method has length 0");
+ return false;
+ }
+
if (m->jcodelength > 65535) {
*exceptionptr =
new_classformaterror(c,
s8 starttime;
s8 stoptime;
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- compiler_lock();
- tables_lock();
-#else
- intsDisable();
-#endif
-#endif
+ /* enter a monitor on the class */
+
+ builtin_monitorenter((java_objectheader *) c);
/* maybe the class is already loaded */
if (c->loaded) {
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- tables_unlock();
- compiler_unlock();
-#else
- intsRestore();
-#endif
-#endif
+ builtin_monitorexit((java_objectheader *) c);
return c;
}
new_exception_utfmessage(string_java_lang_NoClassDefFoundError,
c->name);
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- tables_unlock();
- compiler_unlock();
-#else
- intsRestore();
-#endif
-#endif
+ builtin_monitorexit((java_objectheader *) c);
return NULL;
}
loadingtime += (stoptime - starttime);
}
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- tables_unlock();
- compiler_unlock();
-#else
- intsRestore();
-#endif
-#endif
+ /* leave the monitor */
+
+ builtin_monitorexit((java_objectheader *) c);
return r;
}
{
s4 j, m;
s4 i = ic->index;
- vftbl *vftbl = c->vftbl;
+ vftbl_t *vftbl = c->vftbl;
if (i >= vftbl->interfacetablelength)
panic ("Inernal error: interfacetable overflow");
classinfo *comp = NULL;
s4 namelen = c->name->blength;
arraydescriptor *desc;
- vftbl *compvftbl;
+ vftbl_t *compvftbl;
/* Check the component type */
switch (c->name->text[1]) {
s8 starttime;
s8 stoptime;
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- compiler_lock();
- tables_lock();
-#else
- intsDisable();
-#endif
-#endif
+ /* enter a monitor on the class */
+
+ builtin_monitorenter((java_objectheader *) c);
/* maybe the class is already linked */
if (c->linked) {
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- tables_unlock();
- compiler_unlock();
-#else
- intsRestore();
-#endif
-#endif
+ builtin_monitorexit((java_objectheader *) c);
return c;
}
loadingtime += (stoptime - starttime);
}
-#if defined(USE_THREADS)
-#if defined(NATIVE_THREADS)
- tables_unlock();
- compiler_unlock();
-#else
- intsRestore();
-#endif
-#endif
+ /* leave the monitor */
+
+ builtin_monitorexit((java_objectheader *) c);
return r;
}
s4 interfacetablelength; /* interface table length */
classinfo *super = c->super; /* super class */
classinfo *ic, *c2; /* intermediate class variables */
- vftbl *v; /* vftbl of current class */
+ vftbl_t *v; /* vftbl of current class */
s4 i; /* interface/method/field counter */
arraydescriptor *arraydesc = NULL; /* descriptor for array classes */
}
}
-#ifdef STATISTICS
+#if defined(STATISTICS)
if (opt_stat)
count_vftbl_len +=
- sizeof(vftbl) + (sizeof(methodptr) * (vftbllength - 1));
+ sizeof(vftbl_t) + (sizeof(methodptr) * (vftbllength - 1));
#endif
/* compute interfacetable length */
/* allocate virtual function table */
- v = (vftbl*) mem_alloc(sizeof(vftbl) + sizeof(methodptr) *
+ v = (vftbl_t*) mem_alloc(sizeof(vftbl_t) + sizeof(methodptr) *
(vftbllength - 1) + sizeof(methodptr*) *
(interfacetablelength - (interfacetablelength > 0)));
- v = (vftbl*) (((methodptr*) v) + (interfacetablelength - 1) *
+ v = (vftbl_t*) (((methodptr*) v) + (interfacetablelength - 1) *
(interfacetablelength > 1));
c->header.vftbl = c->vftbl = v;
/* utf_display_classname(c->name);printf(", c->header.vftbl=%p\n", c->header.vftbl); */
v->interfacevftbllength = MNEW(s4, interfacetablelength);
-#ifdef STATISTICS
+#if defined(STATISTICS)
if (opt_stat)
count_vftbl_len += (4 + sizeof(s4)) * v->interfacetablelength;
#endif
void class_free(classinfo *c)
{
s4 i;
- vftbl *v;
+ vftbl_t *v;
class_freecpool(c);
}
MFREE(v->interfacevftbllength, s4, v->interfacetablelength);
- i = sizeof(vftbl) + sizeof(methodptr) * (v->vftbllength - 1) +
+ i = sizeof(vftbl_t) + sizeof(methodptr) * (v->vftbllength - 1) +
sizeof(methodptr*) * (v->interfacetablelength -
(v->interfacetablelength > 0));
- v = (vftbl*) (((methodptr*) v) - (v->interfacetablelength - 1) *
+ v = (vftbl_t*) (((methodptr*) v) - (v->interfacetablelength - 1) *
(v->interfacetablelength > 1));
mem_free(v, i);
}
blockInts = b;
#endif
- /* we have an exception */
+ /* we have an exception or error */
if (*exceptionptr) {
- java_objectheader *xptr;
- java_objectheader *cause;
+ /* is this an exception, than wrap it */
+ if (builtin_instanceof(*exceptionptr, class_java_lang_Exception)) {
+ java_objectheader *xptr;
+ java_objectheader *cause;
- /* class is NOT initialized */
- c->initialized = false;
+ /* class is NOT initialized */
+ c->initialized = false;
- /* get the cause */
- cause = *exceptionptr;
+ /* get the cause */
+ cause = *exceptionptr;
- /* clear exception, because we are calling jit code again */
- *exceptionptr = NULL;
+ /* clear exception, because we are calling jit code again */
+ *exceptionptr = NULL;
- /* wrap the exception */
- xptr =
- new_exception_throwable(string_java_lang_ExceptionInInitializerError,
- (java_lang_Throwable *) cause);
+ /* wrap the exception */
+ xptr =
+ new_exception_throwable(string_java_lang_ExceptionInInitializerError,
+ (java_lang_Throwable *) cause);
- if (*exceptionptr) {
- panic("problem");
- }
+ /* XXX should we exit here? */
+ if (*exceptionptr)
+ throw_exception();
- /* set new exception */
- *exceptionptr = xptr;
+ /* set new exception */
+ *exceptionptr = xptr;
+ }
return NULL;
}
void loader_compute_subclasses(classinfo *c)
{
-#if defined(USE_THREADS) && !defined(NATIVE_THREADS)
+#if defined(USE_THREADS)
+#if defined(NATIVE_THREADS)
+ compiler_lock();
+#else
intsDisable();
+#endif
#endif
if (!(c->flags & ACC_INTERFACE)) {
loader_compute_class_values(class_java_lang_Object);
}
-#if defined(USE_THREADS) && !defined(NATIVE_THREADS)
+#if defined(USE_THREADS)
+#if defined(NATIVE_THREADS)
+ compiler_unlock();
+#else
intsRestore();
#endif
+#endif
}