1 // natField.cc - Implementation of java.lang.reflect.Field native methods.
2
3 /* Copyright (C) 1999, 2000, 2001, 2003 Free Software Foundation
4
5 This file is part of libgcj.
6
7 This software is copyrighted work licensed under the terms of the
8 Libgcj License. Please consult the file "LIBGCJ_LICENSE" for
9 details. */
10
11 #include <config.h>
12
13 #include <stdlib.h>
14
15 #include <jvm.h>
16 #include <gcj/cni.h>
17 #include <java-stack.h>
18 #include <java/lang/reflect/Array.h>
19 #include <java/lang/ArrayIndexOutOfBoundsException.h>
20 #include <java/lang/IllegalArgumentException.h>
21 #include <java/lang/Byte.h>
22 #include <java/lang/Short.h>
23 #include <java/lang/Integer.h>
24 #include <java/lang/Long.h>
25 #include <java/lang/Float.h>
26 #include <java/lang/Double.h>
27 #include <java/lang/Boolean.h>
28 #include <java/lang/Character.h>
29
30 jobject
newInstance(jclass componentType,jint length)31 java::lang::reflect::Array::newInstance (jclass componentType, jint length)
32 {
33 if (componentType->isPrimitive())
34 {
35 // We could check for this in _Jv_NewPrimArray, but that seems
36 // like needless overhead when the only real route to this
37 // problem is here.
38 if (componentType == JvPrimClass (void))
39 throw new java::lang::IllegalArgumentException ();
40 return _Jv_NewPrimArray (componentType, length);
41 }
42 else
43 // FIXME: class loader?
44 return JvNewObjectArray (length, componentType, NULL);
45 }
46
47 jobject
newInstance(jclass componentType,jintArray dimensions)48 java::lang::reflect::Array::newInstance (jclass componentType,
49 jintArray dimensions)
50 {
51 jint ndims = dimensions->length;
52 if (ndims == 0)
53 throw new java::lang::IllegalArgumentException ();
54 jint* dims = elements (dimensions);
55 if (ndims == 1)
56 return newInstance (componentType, dims[0]);
57
58 Class *caller = _Jv_StackTrace::GetCallingClass (&Array::class$);
59 ClassLoader *caller_loader = NULL;
60 if (caller)
61 caller_loader = caller->getClassLoaderInternal();
62
63 jclass arrayType = componentType;
64 for (int i = 0; i < ndims; i++)
65 arrayType = _Jv_GetArrayClass (arrayType, caller_loader);
66
67 return _Jv_NewMultiArray (arrayType, ndims, dims);
68 }
69
70 jint
getLength(jobject array)71 java::lang::reflect::Array::getLength (jobject array)
72 {
73 jclass arrayType = array->getClass();
74 if (! arrayType->isArray ())
75 throw new java::lang::IllegalArgumentException;
76 return ((__JArray*) array)->length;
77 }
78
79 jclass
getElementType(jobject array,jint index)80 java::lang::reflect::Array::getElementType (jobject array, jint index)
81 {
82 jclass arrayType = array->getClass();
83 if (! arrayType->isArray ())
84 throw new java::lang::IllegalArgumentException;
85 jint length = ((__JArray*) array)->length;
86 if ((_Jv_uint) index >= (_Jv_uint) length)
87 _Jv_ThrowBadArrayIndex(index);
88 return arrayType->getComponentType ();
89 }
90
91 jboolean
getBoolean(jobject array,jint index)92 java::lang::reflect::Array::getBoolean (jobject array, jint index)
93 {
94 jclass elementType = getElementType (array, index);
95 if (elementType == JvPrimClass (boolean))
96 return elements ((jbooleanArray) array) [index];
97 throw new java::lang::IllegalArgumentException;
98 }
99
100 jchar
getChar(jobject array,jint index)101 java::lang::reflect::Array::getChar (jobject array, jint index)
102 {
103 jclass elementType = getElementType (array, index);
104 if (elementType == JvPrimClass (char))
105 return elements ((jcharArray) array) [index];
106 throw new java::lang::IllegalArgumentException;
107 }
108
109 jbyte
getByte(jobject array,jint index)110 java::lang::reflect::Array::getByte (jobject array, jint index)
111 {
112 jclass elementType = getElementType (array, index);
113 if (elementType == JvPrimClass (byte))
114 return elements ((jbyteArray) array) [index];
115 throw new java::lang::IllegalArgumentException;
116 }
117
118 jshort
getShort(jobject array,jint index)119 java::lang::reflect::Array::getShort (jobject array, jint index)
120 {
121 jclass elementType = getElementType (array, index);
122 if (elementType == JvPrimClass (short))
123 return elements ((jshortArray) array) [index];
124 if (elementType == JvPrimClass (byte))
125 return elements ((jbyteArray) array) [index];
126 throw new java::lang::IllegalArgumentException;
127 }
128
129 jint
getInt(jobject array,jint index)130 java::lang::reflect::Array::getInt (jobject array, jint index)
131 {
132 jclass elementType = getElementType (array, index);
133 if (elementType == JvPrimClass (int))
134 return elements ((jintArray) array) [index];
135 if (elementType == JvPrimClass (short))
136 return elements ((jshortArray) array) [index];
137 if (elementType == JvPrimClass (byte))
138 return elements ((jbyteArray) array) [index];
139 if (elementType == JvPrimClass (char))
140 return elements ((jcharArray) array) [index];
141 throw new java::lang::IllegalArgumentException;
142 }
143
144 jlong
getLong(jobject array,jint index)145 java::lang::reflect::Array::getLong (jobject array, jint index)
146 {
147 jclass elementType = getElementType (array, index);
148 if (elementType == JvPrimClass (long))
149 return elements ((jlongArray) array) [index];
150 if (elementType == JvPrimClass (int))
151 return elements ((jintArray) array) [index];
152 if (elementType == JvPrimClass (short))
153 return elements ((jshortArray) array) [index];
154 if (elementType == JvPrimClass (byte))
155 return elements ((jbyteArray) array) [index];
156 if (elementType == JvPrimClass (char))
157 return elements ((jcharArray) array) [index];
158 throw new java::lang::IllegalArgumentException;
159 }
160
161 jfloat
getFloat(jobject array,jint index)162 java::lang::reflect::Array::getFloat (jobject array, jint index)
163 {
164 jclass elementType = getElementType (array, index);
165 if (elementType == JvPrimClass (float))
166 return elements ((jfloatArray) array) [index];
167 if (elementType == JvPrimClass (long))
168 return elements ((jlongArray) array) [index];
169 if (elementType == JvPrimClass (int))
170 return elements ((jintArray) array) [index];
171 if (elementType == JvPrimClass (short))
172 return elements ((jshortArray) array) [index];
173 if (elementType == JvPrimClass (byte))
174 return elements ((jbyteArray) array) [index];
175 if (elementType == JvPrimClass (char))
176 return elements ((jcharArray) array) [index];
177 throw new java::lang::IllegalArgumentException;
178 }
179
180 jdouble
getDouble(jobject array,jint index)181 java::lang::reflect::Array::getDouble (jobject array, jint index)
182 {
183 jclass elementType = getElementType (array, index);
184 if (elementType == JvPrimClass (double))
185 return elements ((jdoubleArray) array) [index];
186 if (elementType == JvPrimClass (float))
187 return elements ((jfloatArray) array) [index];
188 if (elementType == JvPrimClass (long))
189 return elements ((jlongArray) array) [index];
190 if (elementType == JvPrimClass (int))
191 return elements ((jintArray) array) [index];
192 if (elementType == JvPrimClass (short))
193 return elements ((jshortArray) array) [index];
194 if (elementType == JvPrimClass (byte))
195 return elements ((jbyteArray) array) [index];
196 if (elementType == JvPrimClass (char))
197 return elements ((jcharArray) array) [index];
198 throw new java::lang::IllegalArgumentException;
199 }
200
201 jobject
get(jobject array,jint index)202 java::lang::reflect::Array::get (jobject array, jint index)
203 {
204 jclass elementType = getElementType (array, index);
205 if (! elementType->isPrimitive ())
206 return elements ((jobjectArray) array) [index];
207 if (elementType == JvPrimClass (double))
208 return new java::lang::Double (elements ((jdoubleArray) array) [index]);
209 if (elementType == JvPrimClass (float))
210 return new java::lang::Float (elements ((jfloatArray) array) [index]);
211 if (elementType == JvPrimClass (long))
212 return new java::lang::Long (elements ((jlongArray) array) [index]);
213 if (elementType == JvPrimClass (int))
214 return new java::lang::Integer (elements ((jintArray) array) [index]);
215 if (elementType == JvPrimClass (short))
216 return new java::lang::Short (elements ((jshortArray) array) [index]);
217 if (elementType == JvPrimClass (byte))
218 return new java::lang::Byte (elements ((jbyteArray) array) [index]);
219 if (elementType == JvPrimClass (char))
220 return new java::lang::Character (elements ((jcharArray) array) [index]);
221 if (elementType == JvPrimClass (boolean))
222 {
223 _Jv_InitClass (&java::lang::Boolean::class$);
224 if (elements ((jbooleanArray) array) [index])
225 return java::lang::Boolean::TRUE;
226 else
227 return java::lang::Boolean::FALSE;
228 }
229 throw new java::lang::IllegalArgumentException;
230 }
231
232 void
setChar(jobject array,jint index,jchar value)233 java::lang::reflect::Array::setChar (jobject array, jint index, jchar value)
234 {
235 jclass elementType = getElementType (array, index);
236 if (elementType == JvPrimClass (char))
237 elements ((jcharArray) array) [index] = value;
238 else if (elementType == JvPrimClass (int))
239 elements ((jintArray) array) [index] = value;
240 else if (elementType == JvPrimClass (long))
241 elements ((jlongArray) array) [index] = value;
242 else if (elementType == JvPrimClass (float))
243 elements ((jfloatArray) array) [index] = value;
244 else if (elementType == JvPrimClass (double))
245 elements ((jdoubleArray) array) [index] = value;
246 else
247 throw new java::lang::IllegalArgumentException;
248 }
249
250 void
setByte(jobject array,jint index,jbyte value)251 java::lang::reflect::Array::setByte (jobject array, jint index, jbyte value)
252 {
253 jclass elementType = getElementType (array, index);
254 if (elementType == JvPrimClass (byte))
255 elements ((jbyteArray) array) [index] = value;
256 else if (elementType == JvPrimClass (short))
257 elements ((jshortArray) array) [index] = value;
258 else if (elementType == JvPrimClass (int))
259 elements ((jintArray) array) [index] = value;
260 else if (elementType == JvPrimClass (long))
261 elements ((jlongArray) array) [index] = value;
262 else if (elementType == JvPrimClass (float))
263 elements ((jfloatArray) array) [index] = value;
264 else if (elementType == JvPrimClass (double))
265 elements ((jdoubleArray) array) [index] = value;
266 else
267 throw new java::lang::IllegalArgumentException;
268 }
269
270 void
setShort(jobject array,jint index,jshort value)271 java::lang::reflect::Array::setShort (jobject array, jint index, jshort value)
272 {
273 jclass elementType = getElementType (array, index);
274 if (elementType == JvPrimClass (short))
275 elements ((jshortArray) array) [index] = value;
276 else if (elementType == JvPrimClass (int))
277 elements ((jintArray) array) [index] = value;
278 else if (elementType == JvPrimClass (long))
279 elements ((jlongArray) array) [index] = value;
280 else if (elementType == JvPrimClass (float))
281 elements ((jfloatArray) array) [index] = value;
282 else if (elementType == JvPrimClass (double))
283 elements ((jdoubleArray) array) [index] = value;
284 else
285 throw new java::lang::IllegalArgumentException;
286 }
287
288 void
setInt(jobject array,jint index,jint value)289 java::lang::reflect::Array::setInt (jobject array, jint index, jint value)
290 {
291 jclass elementType = getElementType (array, index);
292 if (elementType == JvPrimClass (int))
293 elements ((jintArray) array) [index] = value;
294 else if (elementType == JvPrimClass (long))
295 elements ((jlongArray) array) [index] = value;
296 else if (elementType == JvPrimClass (float))
297 elements ((jfloatArray) array) [index] = value;
298 else if (elementType == JvPrimClass (double))
299 elements ((jdoubleArray) array) [index] = value;
300 else
301 throw new java::lang::IllegalArgumentException;
302 }
303
304 void
setLong(jobject array,jint index,jlong value)305 java::lang::reflect::Array::setLong (jobject array, jint index, jlong value)
306 {
307 jclass elementType = getElementType (array, index);
308 if (elementType == JvPrimClass (long))
309 elements ((jlongArray) array) [index] = value;
310 else if (elementType == JvPrimClass (float))
311 elements ((jfloatArray) array) [index] = value;
312 else if (elementType == JvPrimClass (double))
313 elements ((jdoubleArray) array) [index] = value;
314 else
315 throw new java::lang::IllegalArgumentException;
316 }
317
318 void
setFloat(jobject array,jint index,jfloat value)319 java::lang::reflect::Array::setFloat (jobject array, jint index, jfloat value)
320 {
321 jclass elementType = getElementType (array, index);
322 if (elementType == JvPrimClass (float))
323 elements ((jfloatArray) array) [index] = value;
324 else if (elementType == JvPrimClass (double))
325 elements ((jdoubleArray) array) [index] = value;
326 else
327 throw new java::lang::IllegalArgumentException;
328 }
329
330 void
setDouble(jobject array,jint index,jdouble value)331 java::lang::reflect::Array::setDouble (jobject array, jint index, jdouble value)
332 {
333 jclass elementType = getElementType (array, index);
334 if (elementType == JvPrimClass (double))
335 elements ((jdoubleArray) array) [index] = value;
336 else
337 throw new java::lang::IllegalArgumentException;
338 }
339
340 void
setBoolean(jobject array,jint index,jboolean value)341 java::lang::reflect::Array::setBoolean (jobject array,
342 jint index, jboolean value)
343 {
344 jclass elementType = getElementType (array, index);
345 if (elementType == JvPrimClass (boolean))
346 elements ((jbooleanArray) array) [index] = value;
347 else
348 throw new java::lang::IllegalArgumentException;
349 }
350
351 void
set(jobject array,jint index,jobject value,jclass elType)352 java::lang::reflect::Array::set (jobject array, jint index,
353 jobject value, jclass elType)
354 {
355 // We don't have to call getElementType here, or check INDEX,
356 // because it was already done in the Java wrapper.
357 if (value != NULL && ! _Jv_IsInstanceOf (value, elType))
358 throw new java::lang::IllegalArgumentException;
359 elements ((jobjectArray) array) [index] = value;
360 }
361