compile and run again on alpha. No new features from i386 ported yet. It only runs...
[cacao.git] / src / native / vm / VMThrowable.c
1 #include "global.h"
2 #include "jni.h"
3 #include "java_lang_Throwable.h"
4 #include "java_lang_VMThrowable.h"
5 #include "asmpart.h"
6 #include "loader.h"
7 #include "builtin.h"
8 #include "tables.h"
9 #include "native.h"
10
11
12 /*
13  * Class:     java/lang/VMThrowable
14  * Method:    fillInStackTrace
15  * Signature: (Ljava/lang/Throwable;)Ljava/lang/VMThrowable;
16  */
17 JNIEXPORT struct java_lang_VMThrowable* JNICALL Java_java_lang_VMThrowable_fillInStackTrace(JNIEnv *env,
18          jclass clazz, struct java_lang_Throwable* par1) {
19
20         classinfo *class_java_lang_VMThrowable=0;
21         java_lang_VMThrowable *vmthrow;
22
23         log_text("java_lang_VMThrowable");
24
25         if (!class_java_lang_VMThrowable)
26                 class_java_lang_VMThrowable = class_new(utf_new_char ("java/lang/VMThrowable"));
27
28         if (class_java_lang_VMThrowable==0)
29                 panic("Needed class java.lang.VMThrowable missing");
30
31         vmthrow=(java_lang_VMThrowable*)native_new_and_init(class_java_lang_VMThrowable);
32
33         if (vmthrow==0)
34                 panic("Needed instance of class  java.lang.VMThrowable could not be created");
35         
36
37
38 #ifdef __I386__
39         (void)asm_get_stackTrace(&(vmthrow->vmData));
40 #else
41         vmthrow->vmData=0;
42 #endif
43         return vmthrow;
44 }
45
46
47
48 java_objectarray* generateStackTraceArray(JNIEnv *env,stacktraceelement *source,long size) {
49         long resultPos;
50         methodinfo *constructor;
51         classinfo *class_stacktraceelement;
52         java_objectarray *array_stacktraceelement;
53         class_stacktraceelement = (classinfo *) loader_load(utf_new_char ("java/lang/StackTraceElement"));
54
55         if (!class_stacktraceelement)
56                 return 0;
57
58
59         constructor=class_findmethod(class_stacktraceelement,utf_new_char("<init>"),
60                 utf_new_char("(Ljava/lang/String;ILjava/lang/String;Ljava/lang/String;Z)V"));
61         if (!constructor)
62                 panic("java.lang.StackTraceElement misses needed constructor"); 
63
64         array_stacktraceelement = builtin_anewarray(size, class_stacktraceelement);
65
66         if (!array_stacktraceelement)
67                 return 0;
68
69 /*      printf("Should return an array with %ld element(s)\n",size);*/
70         size--;
71         
72         
73         for(resultPos=0;size>=0;resultPos++,size--) {
74                 java_objectheader *element=builtin_new(class_stacktraceelement);
75                 if (!element) {
76                         panic("Memory for stack trace element could not be allocated");
77                 }
78 #ifdef __GNUC__
79 #warning call constructor once jni is fixed to allow more than three parameters
80 #endif
81 #if 0
82                 (*env)->CallVoidMethod(env,element,constructor,
83                         javastring_new(source[size].method->class->sourcefile),
84                         source[size].linenumber,
85                         javastring_new(source[size].method->class->name),
86                         javastring_new(source[size].method->name),
87                         source[size].method->flags & ACC_NATIVE);
88 #else
89                 if (!(source[size].method->flags & ACC_NATIVE))setfield_critical(class_stacktraceelement,element,"fileName",          
90                 "Ljava/lang/String;",  jobject, 
91                 (jobject) javastring_new(source[size].method->class->sourcefile));
92                 setfield_critical(class_stacktraceelement,element,"className",          "Ljava/lang/String;",  jobject, 
93                 (jobject) javastring_new(source[size].method->class->name));
94                 setfield_critical(class_stacktraceelement,element,"methodName",          "Ljava/lang/String;",  jobject, 
95                 (jobject) javastring_new(source[size].method->name));
96                 setfield_critical(class_stacktraceelement,element,"lineNumber",          "I",  jint, 
97                 (jint) ((source[size].method->flags & ACC_NATIVE) ? -1:(source[size].linenumber)));
98                 setfield_critical(class_stacktraceelement,element,"isNative",          "Z",  jboolean, 
99                 (jboolean) ((source[size].method->flags & ACC_NATIVE) ? 1:0));
100
101
102 #endif                  
103
104                 array_stacktraceelement->data[resultPos]=element;
105         }
106
107         return array_stacktraceelement;
108
109 }
110
111
112
113 /*
114  * Class:     java/lang/VMThrowable
115  * Method:    getStackTrace
116  * Signature: (Ljava/lang/Throwable;)[Ljava/lang/StackTraceElement;
117  */
118 JNIEXPORT java_objectarray* JNICALL Java_java_lang_VMThrowable_getStackTrace(JNIEnv *env, 
119         struct java_lang_VMThrowable* this, struct java_lang_Throwable* par1) {
120
121         long  pos;
122         long  maxpos;
123         utf*  classname=par1->header.vftbl->class->name;
124         utf*  init=utf_new_char("<init>");
125         utf*  throwable=utf_new_char("java/lang/Throwable");
126         stacktraceelement *el=(stacktraceelement*)this->vmData;
127
128 /*      log_text("Java_java_lang_VMThrowable_getStackTrace");
129         utf_display(par1->header.vftbl->class->name);
130         printf("\n----------------------------------------------\n");*/
131
132         if (el==0) {
133                 return generateStackTraceArray(env,el,0);
134         }       
135         for (pos=0;el[pos].method!=0;pos++);
136         if (pos==0) {
137                 panic("Stacktrace cannot have zero length");
138         }
139         pos--;
140         pos--;
141         maxpos=pos;
142         if ( (el[pos].method->class->name==throwable)  && (el[pos].method->name==init)  ) {
143                 for (; (pos>=0) && (el[pos].method->name==init) && (el[pos].method->class->name!=classname);pos--);
144                 pos --;
145                 if (pos<0) {
146                         panic("Invalid stack trace for Throwable.getStackTrace()");
147                 }
148         }
149         
150         /* build the result array*/
151         pos++; /*arraysize*/
152         return generateStackTraceArray(env,el,pos);     
153
154 }
155
156
157
158
159