1 /* native/vm/VMThrowable.c - java/lang/VMThrowable
3 Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
4 R. Grafl, A. Krall, C. Kruegel, C. Oates, R. Obermaisser,
5 M. Probst, S. Ring, E. Steiner, C. Thalinger, D. Thuernbeck,
6 P. Tomsich, J. Wenninger
8 This file is part of CACAO.
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.
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.
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., 59 Temple Place - Suite 330, Boston, MA
25 Contact: cacao@complang.tuwien.ac.at
27 Authors: Joseph Wenninger
29 $Id: VMThrowable.c 1621 2004-11-30 13:06:55Z twisti $
34 #include "native/jni.h"
35 #include "native/native.h"
36 #include "native/include/java_lang_Class.h"
37 #include "native/include/java_lang_Throwable.h"
38 #include "native/include/java_lang_VMClass.h"
39 #include "native/include/java_lang_VMThrowable.h"
40 #include "vm/builtin.h"
41 #include "vm/loader.h"
42 #include "vm/tables.h"
43 #include "vm/jit/asmpart.h"
47 * Class: java/lang/VMThrowable
48 * Method: fillInStackTrace
49 * Signature: (Ljava/lang/Throwable;)Ljava/lang/VMThrowable;
51 JNIEXPORT java_lang_VMThrowable* JNICALL Java_java_lang_VMThrowable_fillInStackTrace(JNIEnv *env, jclass clazz, java_lang_Throwable *par1)
53 classinfo *class_java_lang_VMThrowable = NULL;
54 java_lang_VMThrowable *vmthrow;
56 if (!class_java_lang_VMThrowable)
57 class_java_lang_VMThrowable = class_new(utf_new_char("java/lang/VMThrowable"));
59 if (class_java_lang_VMThrowable == NULL)
60 panic("Needed class java.lang.VMThrowable missing");
62 vmthrow = (java_lang_VMThrowable *) native_new_and_init(class_java_lang_VMThrowable);
65 panic("Needed instance of class java.lang.VMThrowable could not be created");
68 (void) asm_get_stackTrace(&(vmthrow->vmData));
78 java_objectarray* generateStackTraceArray(JNIEnv *env,stacktraceelement *source,long pos,long size)
85 c = class_new(utf_new_char("java/lang/StackTraceElement"));
93 m = class_findmethod(c,
94 utf_new_char("<init>"),
95 utf_new_char("(Ljava/lang/String;ILjava/lang/String;Ljava/lang/String;Z)V"));
98 panic("java.lang.StackTraceElement misses needed constructor");
100 oa = builtin_anewarray(size, c);
105 /* printf("Should return an array with %ld element(s)\n",size);*/
109 for(resultPos=0;pos>=0;resultPos++,pos--) {
110 java_objectheader *element;
112 if (source[pos].method==0) {
117 element=builtin_new(c);
119 panic("Memory for stack trace element could not be allocated");
122 #warning call constructor once jni is fixed to allow more than three parameters
125 (*env)->CallVoidMethod(env,element,m,
126 javastring_new(source[pos].method->class->sourcefile),
127 source[size].linenumber,
128 javastring_new(source[pos].method->class->name),
129 javastring_new(source[pos].method->name),
130 source[pos].method->flags & ACC_NATIVE);
132 if (!(source[pos].method->flags & ACC_NATIVE))setfield_critical(c,element,"fileName",
133 "Ljava/lang/String;", jobject,
134 (jobject) javastring_new(source[pos].method->class->sourcefile));
135 /* setfield_critical(c,element,"className", "Ljava/lang/String;", jobject, */
136 /* (jobject) javastring_new(source[pos].method->class->name)); */
137 setfield_critical(c,element,"declaringClass", "Ljava/lang/String;", jobject,
138 (jobject) Java_java_lang_VMClass_getName(env, NULL, (java_lang_Class *) source[pos].method->class));
139 setfield_critical(c,element,"methodName", "Ljava/lang/String;", jobject,
140 (jobject) javastring_new(source[pos].method->name));
141 setfield_critical(c,element,"lineNumber", "I", jint,
142 (jint) ((source[pos].method->flags & ACC_NATIVE) ? -1:(source[pos].linenumber)));
143 setfield_critical(c,element,"isNative", "Z", jboolean,
144 (jboolean) ((source[pos].method->flags & ACC_NATIVE) ? 1:0));
149 oa->data[resultPos]=element;
158 * Class: java/lang/VMThrowable
159 * Method: getStackTrace
160 * Signature: (Ljava/lang/Throwable;)[Ljava/lang/StackTraceElement;
162 JNIEXPORT java_objectarray* JNICALL Java_java_lang_VMThrowable_getStackTrace(JNIEnv *env, java_lang_VMThrowable *this, java_lang_Throwable *par1)
167 utf* classname=par1->header.vftbl->class->name;
168 utf* init=utf_new_char("<init>");
169 utf* throwable=utf_new_char("java/lang/Throwable");
170 stacktraceelement *el=(stacktraceelement*)this->vmData;
172 /* log_text("Java_java_lang_VMThrowable_getStackTrace");
173 utf_display(par1->header.vftbl->class->name);
174 printf("\n----------------------------------------------\n");*/
178 return generateStackTraceArray(env, el, 0,0);
181 for (pos = 0; !((el[pos].method == 0) && (el[pos].linenumber ==-1)); pos++) {
182 if (el[pos].method==0) sizediff++;
186 panic("Stacktrace cannot have zero length");
192 if (el[pos].method!=0) { /* if == 0 -> some builtin native */
193 if (el[pos].method->class->name == throwable && el[pos].method->name == init) {
194 for (; pos >= 0 && el[pos].method->name == init && el[pos].method->class->name != classname; pos--) {
195 /* log_text("ignoring:");
196 utf_display(el[pos].method->name);
198 utf_display(el[pos].method->class->name);
204 log_text("Invalid stack trace for Throwable.getStackTrace()");
210 /* build the result array*/
213 return generateStackTraceArray(env,el,pos,pos-sizediff);
218 * These are local overrides for various environment variables in Emacs.
219 * Please do not remove this and leave it at the end of the file, where
220 * Emacs will automagically detect them.
221 * ---------------------------------------------------------------------
224 * indent-tabs-mode: t