blob: 2406e545100ac80ed1f8d6bc5cfd16a4d1cdb4a0 [file] [log] [blame]
J. Duke319a3b92007-12-01 00:00:00 +00001/*
2 * Copyright 2003-2004 Sun Microsystems, Inc. All Rights Reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Sun designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Sun in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
22 * CA 95054 USA or visit www.sun.com if you need additional information or
23 * have any questions.
24 */
25
26#include <stdlib.h>
27#include <stdio.h>
28#include <jni.h>
29#include "management.h"
30#include "sun_management_GcInfoBuilder.h"
31
32JNIEXPORT jint JNICALL Java_sun_management_GcInfoBuilder_getNumGcExtAttributes
33 (JNIEnv *env, jobject dummy, jobject gc) {
34 jlong value;
35
36 if (gc == NULL) {
37 JNU_ThrowNullPointerException(env, "Invalid GarbageCollectorMBean");
38 return 0;
39 }
40 value = jmm_interface->GetLongAttribute(env, gc,
41 JMM_GC_EXT_ATTRIBUTE_INFO_SIZE);
42 return (jint) value;
43}
44
45JNIEXPORT void JNICALL Java_sun_management_GcInfoBuilder_fillGcAttributeInfo
46 (JNIEnv *env, jobject dummy, jobject gc,
47 jint num_attributes, jobjectArray attributeNames,
48 jcharArray types, jobjectArray descriptions) {
49
50 jmmExtAttributeInfo* ext_att_info;
51 jchar* nativeTypes;
52 jstring attName = NULL;
53 jstring desc = NULL;
54 jint ret = 0;
55 jint i;
56
57 if (gc == NULL) {
58 JNU_ThrowNullPointerException(env, "Invalid GarbageCollectorMBean");
59 return;
60 }
61
62 if (num_attributes == 0) {
63 JNU_ThrowIllegalArgumentException(env, "Invalid num_attributes");
64 return;
65 }
66
67 ext_att_info = (jmmExtAttributeInfo*) malloc(num_attributes *
68 sizeof(jmmExtAttributeInfo));
69 if (ext_att_info == NULL) {
70 JNU_ThrowOutOfMemoryError(env, 0);
71 return;
72 }
73 ret = jmm_interface->GetGCExtAttributeInfo(env, gc,
74 ext_att_info, num_attributes);
75 if (ret != num_attributes) {
76 JNU_ThrowInternalError(env, "Unexpected num_attributes");
77 free(ext_att_info);
78 return;
79 }
80
81 nativeTypes = (jchar*) malloc(num_attributes * sizeof(jchar));
82 if (nativeTypes == NULL) {
83 free(ext_att_info);
84 JNU_ThrowOutOfMemoryError(env, 0);
85 return;
86 }
87 for (i = 0; i < num_attributes; i++) {
88 nativeTypes[i] = ext_att_info[i].type;
89 attName = (*env)->NewStringUTF(env, ext_att_info[i].name);
90 desc = (*env)->NewStringUTF(env, ext_att_info[i].description);
91 (*env)->SetObjectArrayElement(env, attributeNames, i, attName);
92 (*env)->SetObjectArrayElement(env, descriptions, i, desc);
93 }
94 (*env)->SetCharArrayRegion(env, types, 0, num_attributes, nativeTypes);
95
96 if (ext_att_info != NULL) {
97 free(ext_att_info);
98 }
99 if (nativeTypes != NULL) {
100 free(nativeTypes);
101 }
102}
103
104static void setLongValueAtObjectArray(JNIEnv *env, jobjectArray array,
105 jsize index, jlong value) {
106 static const char* class_name = "java/lang/Long";
107 static const char* signature = "(J)V";
108 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
109
110 (*env)->SetObjectArrayElement(env, array, index, obj);
111}
112
113static void setBooleanValueAtObjectArray(JNIEnv *env, jobjectArray array,
114 jsize index, jboolean value) {
115 static const char* class_name = "java/lang/Boolean";
116 static const char* signature = "(Z)V";
117 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
118
119 (*env)->SetObjectArrayElement(env, array, index, obj);
120}
121
122static void setByteValueAtObjectArray(JNIEnv *env, jobjectArray array,
123 jsize index, jbyte value) {
124 static const char* class_name = "java/lang/Byte";
125 static const char* signature = "(B)V";
126 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
127
128 (*env)->SetObjectArrayElement(env, array, index, obj);
129}
130
131static void setIntValueAtObjectArray(JNIEnv *env, jobjectArray array,
132 jsize index, jint value) {
133 static const char* class_name = "java/lang/Integer";
134 static const char* signature = "(I)V";
135 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
136
137 (*env)->SetObjectArrayElement(env, array, index, obj);
138}
139
140static void setShortValueAtObjectArray(JNIEnv *env, jobjectArray array,
141 jsize index, jshort value) {
142 static const char* class_name = "java/lang/Short";
143 static const char* signature = "(S)V";
144 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
145
146 (*env)->SetObjectArrayElement(env, array, index, obj);
147}
148
149static void setDoubleValueAtObjectArray(JNIEnv *env, jobjectArray array,
150 jsize index, jdouble value) {
151 static const char* class_name = "java/lang/Double";
152 static const char* signature = "(D)V";
153 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
154
155 (*env)->SetObjectArrayElement(env, array, index, obj);
156}
157
158static void setFloatValueAtObjectArray(JNIEnv *env, jobjectArray array,
159 jsize index, jfloat value) {
160 static const char* class_name = "java/lang/Float";
161 static const char* signature = "(D)V";
162 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
163
164 (*env)->SetObjectArrayElement(env, array, index, obj);
165}
166
167static void setCharValueAtObjectArray(JNIEnv *env, jobjectArray array,
168 jsize index, jchar value) {
169 static const char* class_name = "java/lang/Character";
170 static const char* signature = "(C)V";
171 jobject obj = JNU_NewObjectByName(env, class_name, signature, value);
172
173 (*env)->SetObjectArrayElement(env, array, index, obj);
174}
175
176JNIEXPORT jobject JNICALL Java_sun_management_GcInfoBuilder_getLastGcInfo0
177 (JNIEnv *env, jobject builder, jobject gc,
178 jint ext_att_count, jobjectArray ext_att_values, jcharArray ext_att_types,
179 jobjectArray usageBeforeGC, jobjectArray usageAfterGC) {
180
181 jmmGCStat gc_stat;
182 jchar* nativeTypes;
183 jsize i;
184 jvalue v;
185
186 if (gc == NULL) {
187 JNU_ThrowNullPointerException(env, "Invalid GarbageCollectorMBean");
188 return 0;
189 }
190
191 gc_stat.usage_before_gc = usageBeforeGC;
192 gc_stat.usage_after_gc = usageAfterGC;
193 gc_stat.gc_ext_attribute_values_size = ext_att_count;
194 if (ext_att_count > 0) {
195 gc_stat.gc_ext_attribute_values = (jvalue*) malloc(ext_att_count *
196 sizeof(jvalue));
197 if (gc_stat.gc_ext_attribute_values == NULL) {
198 JNU_ThrowOutOfMemoryError(env, 0);
199 return 0;
200 }
201 } else {
202 gc_stat.gc_ext_attribute_values = NULL;
203 }
204
205
206 jmm_interface->GetLastGCStat(env, gc, &gc_stat);
207 if (gc_stat.gc_index == 0) {
208 if (gc_stat.gc_ext_attribute_values != NULL) {
209 free(gc_stat.gc_ext_attribute_values);
210 }
211 return 0;
212 }
213
214 // convert the ext_att_types to native types
215 nativeTypes = (jchar*) malloc(ext_att_count * sizeof(jchar));
216 if (nativeTypes == NULL) {
217 if (gc_stat.gc_ext_attribute_values != NULL) {
218 free(gc_stat.gc_ext_attribute_values);
219 }
220 JNU_ThrowOutOfMemoryError(env, 0);
221 return 0;
222 }
223 (*env)->GetCharArrayRegion(env, ext_att_types, 0, ext_att_count, nativeTypes);
224 for (i = 0; i < ext_att_count; i++) {
225 v = gc_stat.gc_ext_attribute_values[i];
226 switch (nativeTypes[i]) {
227 case 'Z':
228 setBooleanValueAtObjectArray(env, ext_att_values, i, v.z);
229 break;
230 case 'B':
231 setByteValueAtObjectArray(env, ext_att_values, i, v.b);
232 break;
233 case 'C':
234 setCharValueAtObjectArray(env, ext_att_values, i, v.c);
235 break;
236 case 'S':
237 setShortValueAtObjectArray(env, ext_att_values, i, v.s);
238 break;
239 case 'I':
240 setIntValueAtObjectArray(env, ext_att_values, i, v.i);
241 break;
242 case 'J':
243 setLongValueAtObjectArray(env, ext_att_values, i, v.j);
244 break;
245 case 'F':
246 setFloatValueAtObjectArray(env, ext_att_values, i, v.f);
247 break;
248 case 'D':
249 setDoubleValueAtObjectArray(env, ext_att_values, i, v.d);
250 break;
251 default:
252 if (gc_stat.gc_ext_attribute_values != NULL) {
253 free(gc_stat.gc_ext_attribute_values);
254 }
255 if (nativeTypes != NULL) {
256 free(nativeTypes);
257 }
258 JNU_ThrowInternalError(env, "Unsupported attribute type");
259 return 0;
260 }
261 }
262 if (gc_stat.gc_ext_attribute_values != NULL) {
263 free(gc_stat.gc_ext_attribute_values);
264 }
265 if (nativeTypes != NULL) {
266 free(nativeTypes);
267 }
268
269 return JNU_NewObjectByName(env,
270 "com/sun/management/GcInfo",
271 "(Lsun/management/GcInfoBuilder;JJJ[Ljava/lang/management/MemoryUsage;[Ljava/lang/management/MemoryUsage;[Ljava/lang/Object;)V",
272 builder,
273 gc_stat.gc_index,
274 gc_stat.start_time,
275 gc_stat.end_time,
276 usageBeforeGC,
277 usageAfterGC,
278 ext_att_values);
279}