< prev index next >

src/hotspot/share/classfile/verifier.hpp

Print this page

  1 /*
  2  * Copyright (c) 1998, 2024, Oracle and/or its affiliates. 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.
  8  *
  9  * This code is distributed in the hope that it will be useful, but WITHOUT
 10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 12  * version 2 for more details (a copy is included in the LICENSE file that
 13  * accompanied this code).
 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  *
 23  */
 24 
 25 #ifndef SHARE_CLASSFILE_VERIFIER_HPP
 26 #define SHARE_CLASSFILE_VERIFIER_HPP
 27 
 28 #include "classfile/verificationType.hpp"
 29 #include "oops/klass.hpp"
 30 #include "oops/method.hpp"
 31 #include "runtime/handles.hpp"
 32 #include "utilities/exceptions.hpp"
 33 #include "utilities/growableArray.hpp"
 34 #include "utilities/resourceHash.hpp"
 35 







 36 // The verifier class
 37 class Verifier : AllStatic {
 38  public:
 39   enum {
 40     STACKMAP_ATTRIBUTE_MAJOR_VERSION    = 50,
 41     INVOKEDYNAMIC_MAJOR_VERSION         = 51,
 42     NO_RELAX_ACCESS_CTRL_CHECK_VERSION  = 52,
 43     DYNAMICCONSTANT_MAJOR_VERSION       = 55


 44   };
 45 
 46   // Verify the bytecodes for a class.
 47   static bool verify(InstanceKlass* klass, bool should_verify_class, TRAPS);
 48 
 49   static void log_end_verification(outputStream* st, const char* klassName, Symbol* exception_name,
 50                                     oop pending_exception);
 51 
 52   // Return false if the class is loaded by the bootstrap loader,
 53   // or if defineClass was called requesting skipping verification
 54   // -Xverify:all overrides this value
 55   static bool should_verify_for(oop class_loader);
 56 
 57   // Relax certain access checks to enable some broken 1.1 apps to run on 1.2.
 58   static bool relax_access_for(oop class_loader);
 59 
 60   // Print output for class+resolve
 61   static void trace_class_resolution(Klass* resolve_class, InstanceKlass* verify_class);
 62 
 63  private:

131   void reset_frame();
132   void details(outputStream* ss) const;
133   void print_frame(outputStream* ss) const;
134   const StackMapFrame* frame() const { return _frame; }
135   bool is_valid() const { return _origin != NONE; }
136   int index() const { return _index; }
137 
138 #ifdef ASSERT
139   void print_on(outputStream* str) const;
140 #endif
141 };
142 
143 class ErrorContext {
144  private:
145   typedef enum {
146     INVALID_BYTECODE,     // There was a problem with the bytecode
147     WRONG_TYPE,           // Type value was not as expected
148     FLAGS_MISMATCH,       // Frame flags are not assignable
149     BAD_CP_INDEX,         // Invalid constant pool index
150     BAD_LOCAL_INDEX,      // Invalid local index

151     LOCALS_SIZE_MISMATCH, // Frames have differing local counts
152     STACK_SIZE_MISMATCH,  // Frames have different stack sizes

153     STACK_OVERFLOW,       // Attempt to push onto a full expression stack
154     STACK_UNDERFLOW,      // Attempt to pop and empty expression stack
155     MISSING_STACKMAP,     // No stackmap for this location and there should be
156     BAD_STACKMAP,         // Format error in stackmap

157     NO_FAULT,             // No error
158     UNKNOWN
159   } FaultType;
160 
161   int _bci;
162   FaultType _fault;
163   TypeOrigin _type;
164   TypeOrigin _expected;
165 
166   ErrorContext(int bci, FaultType fault) :
167       _bci(bci), _fault(fault)  {}
168   ErrorContext(int bci, FaultType fault, TypeOrigin type) :
169       _bci(bci), _fault(fault), _type(type)  {}
170   ErrorContext(int bci, FaultType fault, TypeOrigin type, TypeOrigin exp) :
171       _bci(bci), _fault(fault), _type(type), _expected(exp)  {}
172 
173  public:
174   ErrorContext() : _bci(-1), _fault(NO_FAULT) {}
175 
176   static ErrorContext bad_code(int bci) {

178   }
179   static ErrorContext bad_type(int bci, TypeOrigin type) {
180     return ErrorContext(bci, WRONG_TYPE, type);
181   }
182   static ErrorContext bad_type(int bci, TypeOrigin type, TypeOrigin exp) {
183     return ErrorContext(bci, WRONG_TYPE, type, exp);
184   }
185   static ErrorContext bad_flags(int bci, StackMapFrame* frame) {
186     return ErrorContext(bci, FLAGS_MISMATCH, TypeOrigin::frame(frame));
187   }
188   static ErrorContext bad_flags(int bci, StackMapFrame* cur, StackMapFrame* sm) {
189     return ErrorContext(bci, FLAGS_MISMATCH,
190                         TypeOrigin::frame(cur), TypeOrigin::frame(sm));
191   }
192   static ErrorContext bad_cp_index(int bci, int index) {
193     return ErrorContext(bci, BAD_CP_INDEX, TypeOrigin::bad_index(index));
194   }
195   static ErrorContext bad_local_index(int bci, int index) {
196     return ErrorContext(bci, BAD_LOCAL_INDEX, TypeOrigin::bad_index(index));
197   }



198   static ErrorContext locals_size_mismatch(
199       int bci, StackMapFrame* frame0, StackMapFrame* frame1) {
200     return ErrorContext(bci, LOCALS_SIZE_MISMATCH,
201         TypeOrigin::frame(frame0), TypeOrigin::frame(frame1));
202   }
203   static ErrorContext stack_size_mismatch(
204       int bci, StackMapFrame* frame0, StackMapFrame* frame1) {
205     return ErrorContext(bci, STACK_SIZE_MISMATCH,
206         TypeOrigin::frame(frame0), TypeOrigin::frame(frame1));
207   }





208   static ErrorContext stack_overflow(int bci, StackMapFrame* frame) {
209     return ErrorContext(bci, STACK_OVERFLOW, TypeOrigin::frame(frame));
210   }
211   static ErrorContext stack_underflow(int bci, StackMapFrame* frame) {
212     return ErrorContext(bci, STACK_UNDERFLOW, TypeOrigin::frame(frame));
213   }
214   static ErrorContext missing_stackmap(int bci) {
215     return ErrorContext(bci, MISSING_STACKMAP);
216   }
217   static ErrorContext bad_stackmap(int index, StackMapFrame* frame) {
218     return ErrorContext(0, BAD_STACKMAP, TypeOrigin::frame(frame));
219   }



220 
221   bool is_valid() const { return _fault != NO_FAULT; }
222   int bci() const { return _bci; }
223 
224   void reset_frames() {
225     _type.reset_frame();
226     _expected.reset_frame();
227   }
228 
229   void details(outputStream* ss, const Method* method) const;
230 
231 #ifdef ASSERT
232   void print_on(outputStream* str) const {
233     str->print("error_context(%d, %d,", _bci, _fault);
234     _type.print_on(str);
235     str->print(",");
236     _expected.print_on(str);
237     str->print(")");
238   }
239 #endif

330 
331   void verify_invoke_init(
332     RawBytecodeStream* bcs, u2 ref_index, VerificationType ref_class_type,
333     StackMapFrame* current_frame, u4 code_length, bool in_try_block,
334     bool* this_uninit, const constantPoolHandle& cp, StackMapTable* stackmap_table,
335     TRAPS);
336 
337   // Used by ends_in_athrow() to push all handlers that contain bci onto the
338   // handler_stack, if the handler has not already been pushed on the stack.
339   void push_handlers(ExceptionTable* exhandlers,
340                      GrowableArray<u4>* handler_list,
341                      GrowableArray<u4>* handler_stack,
342                      u4 bci);
343 
344   // Returns true if all paths starting with start_bc_offset end in athrow
345   // bytecode or loop.
346   bool ends_in_athrow(u4 start_bc_offset);
347 
348   void verify_invoke_instructions(
349     RawBytecodeStream* bcs, u4 code_length, StackMapFrame* current_frame,
350     bool in_try_block, bool* this_uninit, VerificationType return_type,
351     const constantPoolHandle& cp, StackMapTable* stackmap_table, TRAPS);
352 
353   VerificationType get_newarray_type(u2 index, int bci, TRAPS);
354   void verify_anewarray(int bci, u2 index, const constantPoolHandle& cp,
355       StackMapFrame* current_frame, TRAPS);
356   void verify_return_value(
357       VerificationType return_type, VerificationType type, int bci,
358       StackMapFrame* current_frame, TRAPS);
359 
360   void verify_iload (int index, StackMapFrame* current_frame, TRAPS);
361   void verify_lload (int index, StackMapFrame* current_frame, TRAPS);
362   void verify_fload (int index, StackMapFrame* current_frame, TRAPS);
363   void verify_dload (int index, StackMapFrame* current_frame, TRAPS);
364   void verify_aload (int index, StackMapFrame* current_frame, TRAPS);
365   void verify_istore(int index, StackMapFrame* current_frame, TRAPS);
366   void verify_lstore(int index, StackMapFrame* current_frame, TRAPS);
367   void verify_fstore(int index, StackMapFrame* current_frame, TRAPS);
368   void verify_dstore(int index, StackMapFrame* current_frame, TRAPS);
369   void verify_astore(int index, StackMapFrame* current_frame, TRAPS);
370   void verify_iinc  (int index, StackMapFrame* current_frame, TRAPS);

427     ss.print("%s", _message);
428     _error_context.details(&ss, _method());
429     return ss.as_string();
430   }
431 
432   // Called when verify or class format errors are encountered.
433   // May throw an exception based upon the mode.
434   void verify_error(ErrorContext ctx, const char* fmt, ...) ATTRIBUTE_PRINTF(3, 4);
435   void class_format_error(const char* fmt, ...) ATTRIBUTE_PRINTF(2, 3);
436 
437   Klass* load_class(Symbol* name, TRAPS);
438 
439   method_signatures_table_type* method_signatures_table() {
440     return &_method_signatures_table;
441   }
442 
443   int change_sig_to_verificationType(
444     SignatureStream* sig_type, VerificationType* inference_type);
445 
446   VerificationType cp_index_to_type(int index, const constantPoolHandle& cp, TRAPS) {
447     return VerificationType::reference_type(cp->klass_name_at(index));

448   }
449 
450   // Keep a list of temporary symbols created during verification because
451   // their reference counts need to be decremented when the verifier object
452   // goes out of scope.  Since these symbols escape the scope in which they're
453   // created, we can't use a TempNewSymbol.
454   Symbol* create_temporary_symbol(const char *s, int length);
455   Symbol* create_temporary_symbol(Symbol* s) {
456     if (s == _previous_symbol) {
457       return s;
458     }
459     if (!s->is_permanent()) {
460       s->increment_refcount();
461       if (_symbols == nullptr) {
462         _symbols = new GrowableArray<Symbol*>(50, 0, nullptr);
463       }
464       _symbols->push(s);
465     }
466     _previous_symbol = s;
467     return s;
468   }
469 
470   TypeOrigin ref_ctx(const char* str);
471 
472 };
473 
474 inline int ClassVerifier::change_sig_to_verificationType(
475     SignatureStream* sig_type, VerificationType* inference_type) {
476   BasicType bt = sig_type->type();
477   switch (bt) {
478     case T_OBJECT:
479     case T_ARRAY:
480       {
481         Symbol* name = sig_type->as_symbol();
482         // Create another symbol to save as signature stream unreferences this symbol.
483         Symbol* name_copy = create_temporary_symbol(name);
484         assert(name_copy == name, "symbols don't match");
485         *inference_type =
486           VerificationType::reference_type(name_copy);
487         return 1;
488       }
489     case T_LONG:
490       *inference_type = VerificationType::long_type();
491       *++inference_type = VerificationType::long2_type();
492       return 2;
493     case T_DOUBLE:
494       *inference_type = VerificationType::double_type();
495       *++inference_type = VerificationType::double2_type();
496       return 2;
497     case T_INT:
498     case T_BOOLEAN:
499     case T_BYTE:
500     case T_CHAR:
501     case T_SHORT:
502       *inference_type = VerificationType::integer_type();
503       return 1;
504     case T_FLOAT:
505       *inference_type = VerificationType::float_type();
506       return 1;

  1 /*
  2  * Copyright (c) 1998, 2025, Oracle and/or its affiliates. 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.
  8  *
  9  * This code is distributed in the hope that it will be useful, but WITHOUT
 10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 12  * version 2 for more details (a copy is included in the LICENSE file that
 13  * accompanied this code).
 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  *
 23  */
 24 
 25 #ifndef SHARE_CLASSFILE_VERIFIER_HPP
 26 #define SHARE_CLASSFILE_VERIFIER_HPP
 27 
 28 #include "classfile/verificationType.hpp"
 29 #include "oops/klass.hpp"
 30 #include "oops/method.hpp"
 31 #include "runtime/handles.hpp"
 32 #include "utilities/exceptions.hpp"
 33 #include "utilities/growableArray.hpp"
 34 #include "utilities/resourceHash.hpp"
 35 
 36 struct NameAndSig {
 37   Symbol* _name;
 38   Symbol* _signature;
 39 
 40   NameAndSig(Symbol* n, Symbol* s) : _name(n), _signature(s) {}
 41 };
 42 
 43 // The verifier class
 44 class Verifier : AllStatic {
 45  public:
 46   enum {
 47     STACKMAP_ATTRIBUTE_MAJOR_VERSION    = 50,
 48     INVOKEDYNAMIC_MAJOR_VERSION         = 51,
 49     NO_RELAX_ACCESS_CTRL_CHECK_VERSION  = 52,
 50     DYNAMICCONSTANT_MAJOR_VERSION       = 55,
 51     VALUE_TYPES_MAJOR_VERSION           = 67,
 52     JAVA_PREVIEW_MINOR_VERSION          = 65535,
 53   };
 54 
 55   // Verify the bytecodes for a class.
 56   static bool verify(InstanceKlass* klass, bool should_verify_class, TRAPS);
 57 
 58   static void log_end_verification(outputStream* st, const char* klassName, Symbol* exception_name,
 59                                     oop pending_exception);
 60 
 61   // Return false if the class is loaded by the bootstrap loader,
 62   // or if defineClass was called requesting skipping verification
 63   // -Xverify:all overrides this value
 64   static bool should_verify_for(oop class_loader);
 65 
 66   // Relax certain access checks to enable some broken 1.1 apps to run on 1.2.
 67   static bool relax_access_for(oop class_loader);
 68 
 69   // Print output for class+resolve
 70   static void trace_class_resolution(Klass* resolve_class, InstanceKlass* verify_class);
 71 
 72  private:

140   void reset_frame();
141   void details(outputStream* ss) const;
142   void print_frame(outputStream* ss) const;
143   const StackMapFrame* frame() const { return _frame; }
144   bool is_valid() const { return _origin != NONE; }
145   int index() const { return _index; }
146 
147 #ifdef ASSERT
148   void print_on(outputStream* str) const;
149 #endif
150 };
151 
152 class ErrorContext {
153  private:
154   typedef enum {
155     INVALID_BYTECODE,     // There was a problem with the bytecode
156     WRONG_TYPE,           // Type value was not as expected
157     FLAGS_MISMATCH,       // Frame flags are not assignable
158     BAD_CP_INDEX,         // Invalid constant pool index
159     BAD_LOCAL_INDEX,      // Invalid local index
160     BAD_STRICT_FIELDS,    // Strict instance fields must be initialized before super constructor
161     LOCALS_SIZE_MISMATCH, // Frames have differing local counts
162     STACK_SIZE_MISMATCH,  // Frames have different stack sizes
163     STRICT_FIELDS_MISMATCH, // Frames have incompatible uninitialized strict instance fields
164     STACK_OVERFLOW,       // Attempt to push onto a full expression stack
165     STACK_UNDERFLOW,      // Attempt to pop and empty expression stack
166     MISSING_STACKMAP,     // No stackmap for this location and there should be
167     BAD_STACKMAP,         // Format error in stackmap
168     WRONG_INLINE_TYPE,    // Mismatched inline type
169     NO_FAULT,             // No error
170     UNKNOWN
171   } FaultType;
172 
173   int _bci;
174   FaultType _fault;
175   TypeOrigin _type;
176   TypeOrigin _expected;
177 
178   ErrorContext(int bci, FaultType fault) :
179       _bci(bci), _fault(fault)  {}
180   ErrorContext(int bci, FaultType fault, TypeOrigin type) :
181       _bci(bci), _fault(fault), _type(type)  {}
182   ErrorContext(int bci, FaultType fault, TypeOrigin type, TypeOrigin exp) :
183       _bci(bci), _fault(fault), _type(type), _expected(exp)  {}
184 
185  public:
186   ErrorContext() : _bci(-1), _fault(NO_FAULT) {}
187 
188   static ErrorContext bad_code(int bci) {

190   }
191   static ErrorContext bad_type(int bci, TypeOrigin type) {
192     return ErrorContext(bci, WRONG_TYPE, type);
193   }
194   static ErrorContext bad_type(int bci, TypeOrigin type, TypeOrigin exp) {
195     return ErrorContext(bci, WRONG_TYPE, type, exp);
196   }
197   static ErrorContext bad_flags(int bci, StackMapFrame* frame) {
198     return ErrorContext(bci, FLAGS_MISMATCH, TypeOrigin::frame(frame));
199   }
200   static ErrorContext bad_flags(int bci, StackMapFrame* cur, StackMapFrame* sm) {
201     return ErrorContext(bci, FLAGS_MISMATCH,
202                         TypeOrigin::frame(cur), TypeOrigin::frame(sm));
203   }
204   static ErrorContext bad_cp_index(int bci, int index) {
205     return ErrorContext(bci, BAD_CP_INDEX, TypeOrigin::bad_index(index));
206   }
207   static ErrorContext bad_local_index(int bci, int index) {
208     return ErrorContext(bci, BAD_LOCAL_INDEX, TypeOrigin::bad_index(index));
209   }
210   static ErrorContext bad_strict_fields(int bci, StackMapFrame* cur) {
211     return ErrorContext(bci, BAD_STRICT_FIELDS, TypeOrigin::frame(cur));
212   }
213   static ErrorContext locals_size_mismatch(
214       int bci, StackMapFrame* frame0, StackMapFrame* frame1) {
215     return ErrorContext(bci, LOCALS_SIZE_MISMATCH,
216         TypeOrigin::frame(frame0), TypeOrigin::frame(frame1));
217   }
218   static ErrorContext stack_size_mismatch(
219       int bci, StackMapFrame* frame0, StackMapFrame* frame1) {
220     return ErrorContext(bci, STACK_SIZE_MISMATCH,
221         TypeOrigin::frame(frame0), TypeOrigin::frame(frame1));
222   }
223   static ErrorContext strict_fields_mismatch(
224       int bci, StackMapFrame* frame0, StackMapFrame* frame1) {
225         return ErrorContext(bci, STRICT_FIELDS_MISMATCH,
226           TypeOrigin::frame(frame0), TypeOrigin::frame(frame1));
227   }
228   static ErrorContext stack_overflow(int bci, StackMapFrame* frame) {
229     return ErrorContext(bci, STACK_OVERFLOW, TypeOrigin::frame(frame));
230   }
231   static ErrorContext stack_underflow(int bci, StackMapFrame* frame) {
232     return ErrorContext(bci, STACK_UNDERFLOW, TypeOrigin::frame(frame));
233   }
234   static ErrorContext missing_stackmap(int bci) {
235     return ErrorContext(bci, MISSING_STACKMAP);
236   }
237   static ErrorContext bad_stackmap(int index, StackMapFrame* frame) {
238     return ErrorContext(0, BAD_STACKMAP, TypeOrigin::frame(frame));
239   }
240   static ErrorContext bad_inline_type(int bci, TypeOrigin type, TypeOrigin exp) {
241     return ErrorContext(bci, WRONG_INLINE_TYPE, type, exp);
242   }
243 
244   bool is_valid() const { return _fault != NO_FAULT; }
245   int bci() const { return _bci; }
246 
247   void reset_frames() {
248     _type.reset_frame();
249     _expected.reset_frame();
250   }
251 
252   void details(outputStream* ss, const Method* method) const;
253 
254 #ifdef ASSERT
255   void print_on(outputStream* str) const {
256     str->print("error_context(%d, %d,", _bci, _fault);
257     _type.print_on(str);
258     str->print(",");
259     _expected.print_on(str);
260     str->print(")");
261   }
262 #endif

353 
354   void verify_invoke_init(
355     RawBytecodeStream* bcs, u2 ref_index, VerificationType ref_class_type,
356     StackMapFrame* current_frame, u4 code_length, bool in_try_block,
357     bool* this_uninit, const constantPoolHandle& cp, StackMapTable* stackmap_table,
358     TRAPS);
359 
360   // Used by ends_in_athrow() to push all handlers that contain bci onto the
361   // handler_stack, if the handler has not already been pushed on the stack.
362   void push_handlers(ExceptionTable* exhandlers,
363                      GrowableArray<u4>* handler_list,
364                      GrowableArray<u4>* handler_stack,
365                      u4 bci);
366 
367   // Returns true if all paths starting with start_bc_offset end in athrow
368   // bytecode or loop.
369   bool ends_in_athrow(u4 start_bc_offset);
370 
371   void verify_invoke_instructions(
372     RawBytecodeStream* bcs, u4 code_length, StackMapFrame* current_frame,
373     bool in_try_block, bool* this_uninit,
374     const constantPoolHandle& cp, StackMapTable* stackmap_table, TRAPS);
375 
376   VerificationType get_newarray_type(u2 index, int bci, TRAPS);
377   void verify_anewarray(int bci, u2 index, const constantPoolHandle& cp,
378       StackMapFrame* current_frame, TRAPS);
379   void verify_return_value(
380       VerificationType return_type, VerificationType type, int bci,
381       StackMapFrame* current_frame, TRAPS);
382 
383   void verify_iload (int index, StackMapFrame* current_frame, TRAPS);
384   void verify_lload (int index, StackMapFrame* current_frame, TRAPS);
385   void verify_fload (int index, StackMapFrame* current_frame, TRAPS);
386   void verify_dload (int index, StackMapFrame* current_frame, TRAPS);
387   void verify_aload (int index, StackMapFrame* current_frame, TRAPS);
388   void verify_istore(int index, StackMapFrame* current_frame, TRAPS);
389   void verify_lstore(int index, StackMapFrame* current_frame, TRAPS);
390   void verify_fstore(int index, StackMapFrame* current_frame, TRAPS);
391   void verify_dstore(int index, StackMapFrame* current_frame, TRAPS);
392   void verify_astore(int index, StackMapFrame* current_frame, TRAPS);
393   void verify_iinc  (int index, StackMapFrame* current_frame, TRAPS);

450     ss.print("%s", _message);
451     _error_context.details(&ss, _method());
452     return ss.as_string();
453   }
454 
455   // Called when verify or class format errors are encountered.
456   // May throw an exception based upon the mode.
457   void verify_error(ErrorContext ctx, const char* fmt, ...) ATTRIBUTE_PRINTF(3, 4);
458   void class_format_error(const char* fmt, ...) ATTRIBUTE_PRINTF(2, 3);
459 
460   Klass* load_class(Symbol* name, TRAPS);
461 
462   method_signatures_table_type* method_signatures_table() {
463     return &_method_signatures_table;
464   }
465 
466   int change_sig_to_verificationType(
467     SignatureStream* sig_type, VerificationType* inference_type);
468 
469   VerificationType cp_index_to_type(int index, const constantPoolHandle& cp, TRAPS) {
470     Symbol* name = cp->klass_name_at(index);
471     return VerificationType::reference_type(name);
472   }
473 
474   // Keep a list of temporary symbols created during verification because
475   // their reference counts need to be decremented when the verifier object
476   // goes out of scope.  Since these symbols escape the scope in which they're
477   // created, we can't use a TempNewSymbol.
478   Symbol* create_temporary_symbol(const char *s, int length);
479   Symbol* create_temporary_symbol(Symbol* s) {
480     if (s == _previous_symbol) {
481       return s;
482     }
483     if (!s->is_permanent()) {
484       s->increment_refcount();
485       if (_symbols == nullptr) {
486         _symbols = new GrowableArray<Symbol*>(50, 0, nullptr);
487       }
488       _symbols->push(s);
489     }
490     _previous_symbol = s;
491     return s;
492   }
493 
494   TypeOrigin ref_ctx(const char* str);
495 
496 };
497 
498 inline int ClassVerifier::change_sig_to_verificationType(
499     SignatureStream* sig_type, VerificationType* inference_type) {
500   BasicType bt = sig_type->type();
501   switch (bt) {
502     case T_OBJECT:
503     case T_ARRAY:
504       {
505         Symbol* name = sig_type->as_symbol();
506         // Create another symbol to save as signature stream unreferences this symbol.
507         Symbol* name_copy = create_temporary_symbol(name);
508         assert(name_copy == name, "symbols don't match");
509         *inference_type = VerificationType::reference_type(name_copy);

510         return 1;
511       }
512     case T_LONG:
513       *inference_type = VerificationType::long_type();
514       *++inference_type = VerificationType::long2_type();
515       return 2;
516     case T_DOUBLE:
517       *inference_type = VerificationType::double_type();
518       *++inference_type = VerificationType::double2_type();
519       return 2;
520     case T_INT:
521     case T_BOOLEAN:
522     case T_BYTE:
523     case T_CHAR:
524     case T_SHORT:
525       *inference_type = VerificationType::integer_type();
526       return 1;
527     case T_FLOAT:
528       *inference_type = VerificationType::float_type();
529       return 1;
< prev index next >