1 /*
2 * Copyright (c) 1997, 2025, Oracle and/or its affiliates. All rights reserved.
3 * Copyright (c) 2021, Azul Systems, Inc. All rights reserved.
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 *
6 * This code is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License version 2 only, as
8 * published by the Free Software Foundation.
9 *
10 * This code is distributed in the hope that it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
13 * version 2 for more details (a copy is included in the LICENSE file that
14 * accompanied this code).
15 *
16 * You should have received a copy of the GNU General Public License version
17 * 2 along with this work; if not, write to the Free Software Foundation,
18 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
19 *
20 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
21 * or visit www.oracle.com if you need additional information or have any
22 * questions.
23 *
24 */
25
26 #ifndef SHARE_RUNTIME_SIGNATURE_HPP
27 #define SHARE_RUNTIME_SIGNATURE_HPP
28
29 #include "classfile/symbolTable.hpp"
30 #include "memory/allocation.hpp"
31 #include "oops/method.hpp"
32
33 // Static routines and parsing loops for processing field and method
34 // descriptors. In the HotSpot sources we call them "signatures".
35 //
36 // A SignatureStream iterates over a Java descriptor (or parts of it).
37 // The syntax is documented in the Java Virtual Machine Specification,
38 // section 4.3.
39 //
40 // The syntax may be summarized as follows:
41 //
42 // MethodType: '(' {FieldType}* ')' (FieldType | 'V')
43 // FieldType: PrimitiveType | ObjectType | ArrayType
44 // PrimitiveType: 'B' | 'C' | 'D' | 'F' | 'I' | 'J' | 'S' | 'Z'
45 // ObjectType: 'L' ClassName ';' | ArrayType
46 // ArrayType: '[' FieldType
47 // ClassName: {UnqualifiedName '/'}* UnqualifiedName
48 // UnqualifiedName: NameChar {NameChar}*
49 // NameChar: ANY_CHAR_EXCEPT('/' | '.' | ';' | '[')
50 //
51 // All of the concrete characters in the above grammar are given
52 // standard manifest constant names of the form JVM_SIGNATURE_x.
53 // Executable code uses these constant names in preference to raw
54 // character constants. Comments and assertion code sometimes use
55 // the raw character constants for brevity.
56 //
57 // The primitive field types (like 'I') correspond 1-1 with type codes
58 // (like T_INT) which form part of the specification of the 'newarray'
59 // instruction (JVMS 6.5, section on newarray). These type codes are
60 // widely used in the HotSpot code. They are joined by ad hoc codes
61 // like T_OBJECT and T_ARRAY (defined in HotSpot but not in the JVMS)
62 // so that each "basic type" of field descriptor (or void return type)
63 // has a corresponding T_x code. Thus, while T_x codes play a very
64 // minor role in the JVMS, they play a major role in the HotSpot
65 // sources. There are fewer than 16 such "basic types", so they fit
66 // nicely into bitfields.
67 //
68 // The syntax of ClassName overlaps slightly with the descriptor
69 // syntaxes. The strings "I" and "(I)V" are both class names
70 // *and* descriptors. If a class name contains any character other
71 // than "BCDFIJSZ()V" it cannot be confused with a descriptor.
72 // Class names inside of descriptors are always contained in an
73 // "envelope" syntax which starts with 'L' and ends with ';'.
74 //
75 // As a confounding factor, array types report their type name strings
76 // in descriptor format. These name strings are easy to recognize,
77 // since they begin with '['. For this reason some API points on
78 // HotSpot look for array descriptors as well as proper class names.
79 //
80 // For historical reasons some API points that accept class names and
81 // array names also look for class names wrapped inside an envelope
82 // (like "LFoo;") and unwrap them on the fly (to a name like "Foo").
83
84 class Signature : AllStatic {
85 private:
86 static bool is_valid_array_signature(const Symbol* sig);
87
88 public:
89
90 // Returns the basic type of a field signature (or T_VOID for "V").
91 // Assumes the signature is a valid field descriptor.
92 // Do not apply this function to class names or method signatures.
93 static BasicType basic_type(const Symbol* signature) {
94 return basic_type(signature->char_at(0));
95 }
96
97 // Returns T_ILLEGAL for an illegal signature char.
98 static BasicType basic_type(int ch);
99
100 // Assuming it is either a class name or signature,
101 // determine if it in fact is an array descriptor.
102 static bool is_array(const Symbol* signature) {
103 return (signature->utf8_length() > 1 &&
104 signature->char_at(0) == JVM_SIGNATURE_ARRAY &&
105 is_valid_array_signature(signature));
106 }
107
108 // Assuming it is either a class name or signature,
109 // determine if it contains a class name plus ';'.
110 static bool has_envelope(const Symbol* signature) {
111 return ((signature->utf8_length() > 0) &&
112 signature->ends_with(JVM_SIGNATURE_ENDCLASS) &&
113 has_envelope(signature->char_at(0)));
114 }
115
116 // Determine if this signature char introduces an
117 // envelope, which is a class name plus ';'.
118 static bool has_envelope(char signature_char) {
119 return (signature_char == JVM_SIGNATURE_CLASS);
120 }
121
122 // Assuming has_envelope is true, return the symbol
123 // inside the envelope, by stripping 'L' and ';'.
124 // Caller is responsible for decrementing the newly created
125 // Symbol's refcount, use TempNewSymbol.
126 static Symbol* strip_envelope(const Symbol* signature);
127
128 // Assuming it's either a field or method descriptor, determine
129 // whether it is in fact a method descriptor:
130 static bool is_method(const Symbol* signature) {
131 return signature->starts_with(JVM_SIGNATURE_FUNC);
132 }
133
134 // Assuming it's a method signature, determine if it must
135 // return void.
136 static bool is_void_method(const Symbol* signature) {
137 assert(is_method(signature), "signature is not for a method");
138 return signature->ends_with(JVM_SIGNATURE_VOID);
139 }
140 };
141
142 // A SignatureIterator uses a SignatureStream to produce BasicType
143 // results, discarding class names. This means it can be accelerated
144 // using a fingerprint mechanism, in many cases, without loss of type
145 // information. The FingerPrinter class computes and caches this
146 // reduced information for faster iteration.
147
148 class SignatureIterator: public ResourceObj {
149 public:
150 typedef uint64_t fingerprint_t;
151
152 protected:
153 Symbol* _signature; // the signature to iterate over
154 BasicType _return_type;
155 fingerprint_t _fingerprint;
156
157 public:
158 // Definitions used in generating and iterating the
159 // bit field form of the signature generated by the
160 // Fingerprinter.
161 enum {
162 fp_static_feature_size = 1,
163 fp_is_static_bit = 1,
164
165 fp_result_feature_size = 4,
166 fp_result_feature_mask = right_n_bits(fp_result_feature_size),
167 fp_parameter_feature_size = 4,
168 fp_parameter_feature_mask = right_n_bits(fp_parameter_feature_size),
169
170 fp_parameters_done = 0, // marker for end of parameters (must be zero)
171
172 // Parameters take up full wordsize, minus the result and static bit fields.
173 // Since fp_parameters_done is zero, termination field arises from shifting
174 // in zero bits, and therefore occupies no extra space.
175 // The sentinel value is all-zero-bits, which is impossible for a true
176 // fingerprint, since at least the result field will be non-zero.
177 fp_max_size_of_parameters = ((BitsPerLong
178 - (fp_result_feature_size + fp_static_feature_size))
179 / fp_parameter_feature_size)
180 };
181
182 static bool fp_is_valid_type(BasicType type, bool for_return_type = false);
183
184 // Sentinel values are zero and not-zero (-1).
185 // No need to protect the sign bit, since every valid return type is non-zero
186 // (even T_VOID), and there are no valid parameter fields which are 0xF (T_VOID).
187 static fingerprint_t zero_fingerprint() { return (fingerprint_t)0; }
188 static fingerprint_t overflow_fingerprint() { return ~(fingerprint_t)0; }
189 static bool fp_is_valid(fingerprint_t fingerprint) {
190 return (fingerprint != zero_fingerprint()) && (fingerprint != overflow_fingerprint());
191 }
192
193 // Constructors
194 SignatureIterator(Symbol* signature, fingerprint_t fingerprint = zero_fingerprint()) {
195 _signature = signature;
196 _return_type = T_ILLEGAL; // sentinel value for uninitialized
197 _fingerprint = zero_fingerprint();
198 if (fingerprint != _fingerprint) {
199 set_fingerprint(fingerprint);
200 }
201 }
202
203 // If the fingerprint is present, we can use an accelerated loop.
204 void set_fingerprint(fingerprint_t fingerprint);
205
206 // Returns the set fingerprint, or zero_fingerprint()
207 // if none has been set already.
208 fingerprint_t fingerprint() const { return _fingerprint; }
209
210 // Iteration
211 // Hey look: There are no virtual methods in this class.
212 // So how is it customized? By calling do_parameters_on
213 // an object which answers to "do_type(BasicType)".
214 // By convention, this object is in the subclass
215 // itself, so the call is "do_parameters_on(this)".
216 // The effect of this is to inline the parsing loop
217 // everywhere "do_parameters_on" is called.
218 // If there is a valid fingerprint in the object,
219 // an improved loop is called which just unpacks the
220 // bitfields from the fingerprint. Otherwise, the
221 // symbol is parsed.
222 template<typename T> inline void do_parameters_on(T* callback); // iterates over parameters only
223 BasicType return_type(); // computes the value on the fly if necessary
224
225 static BasicType fp_return_type(fingerprint_t fingerprint) {
226 assert(fp_is_valid(fingerprint), "invalid fingerprint");
227 return (BasicType) ((fingerprint >> fp_static_feature_size) & fp_result_feature_mask);
228 }
229 static fingerprint_t fp_start_parameters(fingerprint_t fingerprint) {
230 assert(fp_is_valid(fingerprint), "invalid fingerprint");
231 return fingerprint >> (fp_static_feature_size + fp_result_feature_size);
232 }
233 static BasicType fp_next_parameter(fingerprint_t& mask) {
234 int result = (mask & fp_parameter_feature_mask);
235 mask >>= fp_parameter_feature_size;
236 return (BasicType) result;
237 }
238 };
239
240
241 // Specialized SignatureIterators: Used to compute signature specific values.
242
243 class SignatureTypeNames : public SignatureIterator {
244 protected:
245 virtual void type_name(const char* name) = 0;
246
247 friend class SignatureIterator; // so do_parameters_on can call do_type
248 void do_type(BasicType type) {
249 switch (type) {
250 case T_BOOLEAN: type_name("jboolean"); break;
251 case T_CHAR: type_name("jchar" ); break;
252 case T_FLOAT: type_name("jfloat" ); break;
253 case T_DOUBLE: type_name("jdouble" ); break;
254 case T_BYTE: type_name("jbyte" ); break;
255 case T_SHORT: type_name("jshort" ); break;
256 case T_INT: type_name("jint" ); break;
257 case T_LONG: type_name("jlong" ); break;
258 case T_VOID: type_name("void" ); break;
259 case T_ARRAY:
260 case T_OBJECT: type_name("jobject" ); break;
261 default: ShouldNotReachHere();
262 }
263 }
264
265 public:
266 SignatureTypeNames(Symbol* signature) : SignatureIterator(signature) {}
267 };
268
269
270 // Specialized SignatureIterator: Used to compute the argument size.
271
272 class ArgumentSizeComputer: public SignatureIterator {
273 private:
274 int _size;
275 friend class SignatureIterator; // so do_parameters_on can call do_type
276 void do_type(BasicType type) { _size += parameter_type_word_count(type); }
277 public:
278 ArgumentSizeComputer(Symbol* signature);
279 int size() { return _size; }
280 };
281
282
283 class ArgumentCount: public SignatureIterator {
284 private:
285 int _size;
286 friend class SignatureIterator; // so do_parameters_on can call do_type
287 void do_type(BasicType type) { _size++; }
288 public:
289 ArgumentCount(Symbol* signature);
290 int size() { return _size; }
291 };
292
293
294 class ReferenceArgumentCount: public SignatureIterator {
295 private:
296 int _refs;
297 friend class SignatureIterator; // so do_parameters_on can call do_type
298 void do_type(BasicType type) { if (is_reference_type(type)) _refs++; }
299 public:
300 ReferenceArgumentCount(Symbol* signature);
301 int count() { return _refs; }
302 };
303
304
305 // Specialized SignatureIterator: Used to compute the result type.
306
307 class ResultTypeFinder: public SignatureIterator {
308 public:
309 BasicType type() { return return_type(); }
310 ResultTypeFinder(Symbol* signature) : SignatureIterator(signature) { }
311 };
312
313
314 // Fingerprinter computes a unique ID for a given method. The ID
315 // is a bitvector characterizing the methods signature (incl. the receiver).
316 class Fingerprinter: public SignatureIterator {
317 private:
318 fingerprint_t _accumulator;
319 int _param_size;
320 int _stack_arg_slots;
321 int _shift_count;
322 const Method* _method;
323
324 uint _int_args;
325 uint _fp_args;
326
327 void initialize_accumulator() {
328 _accumulator = 0;
329 _shift_count = fp_result_feature_size + fp_static_feature_size;
330 _param_size = 0;
331 _stack_arg_slots = 0;
332 }
333
334 // Out-of-line method does it all in constructor:
335 void compute_fingerprint_and_return_type(bool static_flag = false);
336
337 void initialize_calling_convention(bool static_flag);
338 void do_type_calling_convention(BasicType type);
339
340 friend class SignatureIterator; // so do_parameters_on can call do_type
341
342 void do_type(BasicType type) {
343 assert(fp_is_valid_type(type), "bad parameter type");
344 if (_param_size <= fp_max_size_of_parameters) {
345 _accumulator |= ((fingerprint_t)type << _shift_count);
346 _shift_count += fp_parameter_feature_size;
347 }
348 _param_size += (is_double_word_type(type) ? 2 : 1);
349 do_type_calling_convention(type);
350 }
351
352 public:
353 int size_of_parameters() const { return _param_size; }
354 int num_stack_arg_slots() const { return _stack_arg_slots; }
355
356 // fingerprint() and return_type() are in super class
357
358 Fingerprinter(const methodHandle& method)
359 : SignatureIterator(method->signature()),
360 _method(method()) {
361 compute_fingerprint_and_return_type();
362 }
363 Fingerprinter(Symbol* signature, bool is_static)
364 : SignatureIterator(signature),
365 _method(nullptr) {
366 compute_fingerprint_and_return_type(is_static);
367 }
368 };
369
370
371 // Specialized SignatureIterator: Used for native call purposes
372
373 class NativeSignatureIterator: public SignatureIterator {
374 private:
375 methodHandle _method;
376 // We need separate JNI and Java offset values because in 64 bit mode,
377 // the argument offsets are not in sync with the Java stack.
378 // For example a long takes up 1 "C" stack entry but 2 Java stack entries.
379 int _offset; // The java stack offset
380 int _prepended; // number of prepended JNI parameters (1 JNIEnv, plus 1 mirror if static)
381 int _jni_offset; // the current parameter offset, starting with 0
382
383 friend class SignatureIterator; // so do_parameters_on can call do_type
384 void do_type(BasicType type) {
385 switch (type) {
386 case T_BYTE:
387 case T_BOOLEAN:
388 pass_byte(); _jni_offset++; _offset++;
389 break;
390 case T_CHAR:
391 case T_SHORT:
392 pass_short(); _jni_offset++; _offset++;
393 break;
394 case T_INT:
395 pass_int(); _jni_offset++; _offset++;
396 break;
397 case T_FLOAT:
398 pass_float(); _jni_offset++; _offset++;
399 break;
400 case T_DOUBLE: {
401 int jni_offset = LP64_ONLY(1) NOT_LP64(2);
402 pass_double(); _jni_offset += jni_offset; _offset += 2;
403 break;
404 }
405 case T_LONG: {
406 int jni_offset = LP64_ONLY(1) NOT_LP64(2);
407 pass_long(); _jni_offset += jni_offset; _offset += 2;
408 break;
409 }
410 case T_ARRAY:
411 case T_OBJECT:
412 pass_object(); _jni_offset++; _offset++;
413 break;
414 default:
415 ShouldNotReachHere();
416 }
417 }
418
419 public:
420 methodHandle method() const { return _method; }
421 int offset() const { return _offset; }
422 int jni_offset() const { return _jni_offset + _prepended; }
423 bool is_static() const { return method()->is_static(); }
424 virtual void pass_int() = 0;
425 virtual void pass_long() = 0;
426 virtual void pass_object() = 0; // objects, arrays, inlines
427 virtual void pass_float() = 0;
428 virtual void pass_byte() { pass_int(); };
429 virtual void pass_short() { pass_int(); };
430 #ifdef _LP64
431 virtual void pass_double() = 0;
432 #else
433 virtual void pass_double() { pass_long(); } // may be same as long
434 #endif
435
436 NativeSignatureIterator(const methodHandle& method) : SignatureIterator(method->signature()) {
437 _method = method;
438 _offset = 0;
439 _jni_offset = 0;
440
441 const int JNIEnv_words = 1;
442 const int mirror_words = 1;
443 _prepended = !is_static() ? JNIEnv_words : JNIEnv_words + mirror_words;
444 }
445
446 void iterate() { iterate(Fingerprinter(method()).fingerprint()); }
447
448 // iterate() calls the 3 virtual methods according to the following invocation syntax:
449 //
450 // {pass_int | pass_long | pass_object}
451 //
452 // Arguments are handled from left to right (receiver first, if any).
453 // The offset() values refer to the Java stack offsets but are 0 based and increasing.
454 // The java_offset() values count down to 0, and refer to the Java TOS.
455 // The jni_offset() values increase from 1 or 2, and refer to C arguments.
456 // The method's return type is ignored.
457
458 void iterate(fingerprint_t fingerprint) {
459 set_fingerprint(fingerprint);
460 if (!is_static()) {
461 // handle receiver (not handled by iterate because not in signature)
462 pass_object(); _jni_offset++; _offset++;
463 }
464 do_parameters_on(this);
465 }
466 };
467
468
469 // This is the core parsing logic for iterating over signatures.
470 // All of the previous classes use this for doing their work.
471
472 class SignatureStream : public StackObj {
473 private:
474 const Symbol* _signature;
475 int _begin;
476 int _end;
477 int _limit;
478 int _array_prefix; // count of '[' before the array element descr
479 BasicType _type;
480 int _state;
481 Symbol* _previous_name; // cache the previously looked up symbol to avoid lookups
482 GrowableArray<Symbol*>* _names; // symbols created while parsing that need to be dereferenced
483
484 Symbol* find_symbol();
485
486 enum { _s_field = 0, _s_method = 1, _s_method_return = 3 };
487 void set_done() {
488 _state |= -2; // preserve s_method bit
489 assert(is_done(), "Unable to set state to done");
490 }
491 int scan_type(BasicType bt);
492
493 public:
494 bool at_return_type() const { return _state == (int)_s_method_return; }
495 bool is_done() const { return _state < 0; }
496 void next();
497
498 SignatureStream(const Symbol* signature, bool is_method = true);
499 ~SignatureStream();
500
501 bool is_reference() const { return is_reference_type(_type); }
502 bool is_array() const { return _type == T_ARRAY; }
503 BasicType type() const { return _type; }
504
505 const u1* raw_bytes() const { return _signature->bytes() + _begin; }
506 int raw_length() const { return _end - _begin; }
507 int raw_symbol_begin() const { return _begin + (has_envelope() ? 1 : 0); }
508 int raw_symbol_end() const { return _end - (has_envelope() ? 1 : 0); }
509 char raw_char_at(int i) const {
510 assert(i < _limit, "index for raw_char_at is over the limit");
511 return _signature->char_at(i);
512 }
513
514 // True if there is an embedded class name in this type,
515 // followed by ';'.
516 bool has_envelope() const {
517 if (!Signature::has_envelope(_signature->char_at(_begin)))
518 return false;
519 // this should always be true, but let's test it:
520 assert(_signature->char_at(_end-1) == JVM_SIGNATURE_ENDCLASS, "signature envelope has no semi-colon at end");
521 return true;
522 }
523
524 // return the symbol for chars in symbol_begin()..symbol_end()
525 Symbol* as_symbol() {
526 return find_symbol();
527 }
528
529 // in case you want only the return type:
530 void skip_to_return_type();
531
532 // number of '[' in array prefix
533 int array_prefix_length() {
534 return _type == T_ARRAY ? _array_prefix : 0;
535 }
536
537 // In case you want only the array base type,
538 // reset the stream after skipping some brackets '['.
539 // (The argument is clipped to array_prefix_length(),
540 // and if it ends up as zero this call is a nop.
541 // The default is value skips all brackets '['.)
542 private:
543 int skip_whole_array_prefix();
544 public:
545 int skip_array_prefix(int max_skip_length) {
546 if (_type != T_ARRAY) {
547 return 0;
548 }
549 if (_array_prefix > max_skip_length) {
550 // strip some but not all levels of T_ARRAY
551 _array_prefix -= max_skip_length;
552 _begin += max_skip_length;
553 return max_skip_length;
554 }
555 return skip_whole_array_prefix();
556 }
557 int skip_array_prefix() {
558 if (_type != T_ARRAY) {
559 return 0;
560 }
561 return skip_whole_array_prefix();
562 }
563
564 // free-standing lookups (bring your own CL/PD pair)
565 enum FailureMode { ReturnNull, NCDFError, CachedOrNull };
566
567 Klass* as_klass(Handle class_loader, FailureMode failure_mode, TRAPS);
568 InlineKlass* as_inline_klass(InstanceKlass* holder);
569 oop as_java_mirror(Handle class_loader, FailureMode failure_mode, TRAPS);
570 };
571
572 class SigEntryFilter;
573 typedef GrowableArrayFilterIterator<SigEntry, SigEntryFilter> ExtendedSignature;
574
575 // Used for adapter generation. One SigEntry is used per element of
576 // the signature of the method. Inline type arguments are treated
577 // specially. See comment for InlineKlass::collect_fields().
578 class SigEntry {
579 public:
580 BasicType _bt; // Basic type of the argument
581 int _offset; // Offset of the field in its value class holder for scalarized arguments (-1 otherwise). Used for packing and unpacking.
582 Symbol* _name; // Symbol for printing
583 bool _null_marker; // Is it a null marker? For printing
584
585 SigEntry()
586 : _bt(T_ILLEGAL), _offset(-1), _name(nullptr) {}
587
588 SigEntry(BasicType bt, int offset, Symbol* name, bool null_marker)
589 : _bt(bt), _offset(offset), _name(name), _null_marker(null_marker) {}
590
591 static void add_entry(GrowableArray<SigEntry>* sig, BasicType bt, Symbol* name = nullptr, int offset = -1);
592 static void add_null_marker(GrowableArray<SigEntry>* sig, Symbol* name, int offset);
593 static bool skip_value_delimiters(const GrowableArray<SigEntry>* sig, int i);
594 static int fill_sig_bt(const GrowableArray<SigEntry>* sig, BasicType* sig_bt);
595 static TempNewSymbol create_symbol(const GrowableArray<SigEntry>* sig);
596 };
597
598 class SigEntryFilter {
599 public:
600 bool operator()(const SigEntry& entry) { return entry._bt != T_METADATA && entry._bt != T_VOID; }
601 };
602
603 // Specialized SignatureStream: used for invoking SystemDictionary to either find
604 // or resolve the underlying type when iterating over a
605 // Java descriptor (or parts of it).
606 class ResolvingSignatureStream : public SignatureStream {
607 Klass* _load_origin;
608 bool _handles_cached;
609 Handle _class_loader; // cached when needed
610
611 void initialize_load_origin(Klass* load_origin) {
612 _load_origin = load_origin;
613 _handles_cached = (load_origin == nullptr);
614 }
615 void need_handles() {
616 if (!_handles_cached) {
617 cache_handles();
618 _handles_cached = true;
619 }
620 }
621 void cache_handles();
622
623 public:
624 ResolvingSignatureStream(Symbol* signature, Klass* load_origin, bool is_method = true);
625 ResolvingSignatureStream(Symbol* signature, Handle class_loader, bool is_method = true);
626 ResolvingSignatureStream(const Method* method);
627
628 Klass* as_klass(FailureMode failure_mode, TRAPS) {
629 need_handles();
630 return SignatureStream::as_klass(_class_loader, failure_mode, THREAD);
631 }
632 oop as_java_mirror(FailureMode failure_mode, TRAPS) {
633 if (is_reference()) {
634 need_handles();
635 }
636 return SignatureStream::as_java_mirror(_class_loader, failure_mode, THREAD);
637 }
638 };
639
640 // Here is how all the SignatureIterator classes invoke the
641 // SignatureStream engine to do their parsing.
642 template<typename T> inline
643 void SignatureIterator::do_parameters_on(T* callback) {
644 fingerprint_t unaccumulator = _fingerprint;
645
646 // Check for too many arguments, or missing fingerprint:
647 if (!fp_is_valid(unaccumulator)) {
648 SignatureStream ss(_signature);
649 for (; !ss.at_return_type(); ss.next()) {
650 callback->do_type(ss.type());
651 }
652 // while we are here, capture the return type
653 _return_type = ss.type();
654 } else {
655 // Optimized version of do_parameters when fingerprint is known
656 assert(_return_type != T_ILLEGAL, "return type already captured from fp");
657 unaccumulator = fp_start_parameters(unaccumulator);
658 for (BasicType type; (type = fp_next_parameter(unaccumulator)) != (BasicType)fp_parameters_done; ) {
659 assert(fp_is_valid_type(type), "garbled fingerprint");
660 callback->do_type(type);
661 }
662 }
663 }
664
665 #ifdef ASSERT
666 class SignatureVerifier : public StackObj {
667 public:
668 static bool is_valid_method_signature(const Symbol* sig);
669 static bool is_valid_type_signature(const Symbol* sig);
670 private:
671 static ssize_t is_valid_type(const char*, ssize_t);
672 };
673 #endif
674 #endif // SHARE_RUNTIME_SIGNATURE_HPP