< prev index next >

src/hotspot/share/runtime/sharedRuntime.hpp

Print this page
@@ -23,14 +23,16 @@
   */
  
  #ifndef SHARE_RUNTIME_SHAREDRUNTIME_HPP
  #define SHARE_RUNTIME_SHAREDRUNTIME_HPP
  
+ #include "classfile/compactHashtable.hpp"
  #include "code/codeBlob.hpp"
  #include "code/vmreg.hpp"
  #include "interpreter/linkResolver.hpp"
  #include "memory/allStatic.hpp"
+ #include "memory/metaspaceClosure.hpp"
  #include "memory/resourceArea.hpp"
  #include "runtime/stubDeclarations.hpp"
  #include "utilities/macros.hpp"
  
  class AdapterHandlerEntry;

@@ -114,10 +116,11 @@
    // The handle is dereferenced and the return value is the event writer oop.
    static RuntimeStub* generate_jfr_write_checkpoint();
    // For c2: call to runtime to return a buffer lease.
    static RuntimeStub* generate_jfr_return_lease();
  #endif
+   static void init_adapter_library();
  
    static const char *stub_name(SharedStubId id) {
      assert(id > SharedStubId::NO_STUBID && id < SharedStubId::NUM_STUBIDS, "stub id out of range");
      return _stub_names[(int)id];
    }

@@ -464,16 +467,16 @@
    // that the interpreter before it does any call dispatch will record the current
    // stack pointer in the interpreter frame. On return it will restore the stack
    // pointer as needed. This means the i2c adapter code doesn't need any special
    // handshaking path with compiled code to keep the stack walking correct.
  
-   static AdapterHandlerEntry* generate_i2c2i_adapters(MacroAssembler *_masm,
-                                                       int total_args_passed,
-                                                       int max_arg,
-                                                       const BasicType *sig_bt,
-                                                       const VMRegPair *regs,
-                                                       AdapterFingerPrint* fingerprint);
+   static void generate_i2c2i_adapters(MacroAssembler *_masm,
+                                int total_args_passed,
+                                int max_arg,
+                                const BasicType *sig_bt,
+                                const VMRegPair *regs,
+                                AdapterHandlerEntry* handler);
  
    static void gen_i2c_adapter(MacroAssembler *_masm,
                                int total_args_passed,
                                int comp_args_on_stack,
                                const BasicType *sig_bt,

@@ -565,10 +568,25 @@
    static address handle_wrong_method_abstract(JavaThread* current);
    static address handle_wrong_method_ic_miss(JavaThread* current);
  
    static address handle_unsafe_access(JavaThread* thread, address next_pc);
  
+  private:
+   static PerfTickCounters* _perf_resolve_opt_virtual_total_time;
+   static PerfTickCounters* _perf_resolve_virtual_total_time;
+   static PerfTickCounters* _perf_resolve_static_total_time;
+   static PerfTickCounters* _perf_handle_wrong_method_total_time;
+   static PerfTickCounters* _perf_ic_miss_total_time;
+  public:
+   static uint _ic_miss_ctr;                      // total # of IC misses
+   static uint _wrong_method_ctr;
+   static uint _resolve_static_ctr;
+   static uint _resolve_virtual_ctr;
+   static uint _resolve_opt_virtual_ctr;
+ 
+   static void print_counters_on(outputStream* st);
+ 
  #ifndef PRODUCT
  
    // Collect and print inline cache miss statistics
   private:
    enum { maxICmiss_count = 100 };

@@ -576,15 +594,10 @@
    static int     _ICmiss_count[maxICmiss_count]; // miss counts
    static address _ICmiss_at[maxICmiss_count];    // miss addresses
    static void trace_ic_miss(address at);
  
   public:
-   static uint _ic_miss_ctr;                      // total # of IC misses
-   static uint _wrong_method_ctr;
-   static uint _resolve_static_ctr;
-   static uint _resolve_virtual_ctr;
-   static uint _resolve_opt_virtual_ctr;
    static uint _implicit_null_throws;
    static uint _implicit_div0_throws;
  
    static uint _jbyte_array_copy_ctr;       // Slow-path byte array copy
    static uint _jshort_array_copy_ctr;      // Slow-path short array copy

@@ -624,13 +637,13 @@
    static address nof_inlined_calls_addr()               { return (address)&_nof_inlined_calls; }
    static address nof_static_calls_addr()                { return (address)&_nof_static_calls; }
    static address nof_inlined_static_calls_addr()        { return (address)&_nof_inlined_static_calls; }
    static address nof_interface_calls_addr()             { return (address)&_nof_interface_calls; }
    static address nof_inlined_interface_calls_addr()     { return (address)&_nof_inlined_interface_calls; }
-   static void print_call_statistics(uint64_t comp_total);
-   static void print_ic_miss_histogram();
  
+   static void print_call_statistics_on(outputStream* st);
+   static void print_ic_miss_histogram_on(outputStream* st);
  #endif // PRODUCT
  
    static void print_statistics() PRODUCT_RETURN;
  };
  

@@ -666,19 +679,20 @@
  // routine in their middles and end in a return (instead of ending in a jump).
  // The native wrappers are stored in real nmethods instead of the BufferBlobs
  // used by the adapters.  The code generation happens here because it's very
  // similar to what the adapters have to do.
  
- class AdapterHandlerEntry : public CHeapObj<mtCode> {
+ class AdapterHandlerEntry : public MetaspaceObj {
    friend class AdapterHandlerLibrary;
  
   private:
    AdapterFingerPrint* _fingerprint;
    address _i2c_entry;
    address _c2i_entry;
    address _c2i_unverified_entry;
    address _c2i_no_clinit_check_entry;
+   bool    _linked;
  
  #ifdef ASSERT
    // Captures code and signature used to generate this adapter when
    // verifying adapter equivalence.
    unsigned char* _saved_code;

@@ -690,24 +704,47 @@
                        address c2i_no_clinit_check_entry) :
      _fingerprint(fingerprint),
      _i2c_entry(i2c_entry),
      _c2i_entry(c2i_entry),
      _c2i_unverified_entry(c2i_unverified_entry),
-     _c2i_no_clinit_check_entry(c2i_no_clinit_check_entry)
+     _c2i_no_clinit_check_entry(c2i_no_clinit_check_entry),
+     _linked(false)
  #ifdef ASSERT
      , _saved_code_length(0)
  #endif
    { }
  
    ~AdapterHandlerEntry();
  
   public:
+   static AdapterHandlerEntry* allocate(AdapterFingerPrint* fingerprint,
+                                        address i2c_entry,
+                                        address c2i_entry,
+                                        address c2i_unverified_entry,
+                                        address c2i_no_clinit_check_entry)
+   {
+     return new (mtCode) AdapterHandlerEntry(fingerprint, i2c_entry, c2i_entry, c2i_unverified_entry, c2i_no_clinit_check_entry);
+   }
+ 
+   static void deallocate(AdapterHandlerEntry *handler) {
+     handler->~AdapterHandlerEntry();
+   }
+ 
+   void set_entry_points(address i2c_entry, address c2i_entry, address c2i_unverified_entry, address c2i_no_clinit_check_entry, bool linked = true) {
+     _i2c_entry = i2c_entry;
+     _c2i_entry = c2i_entry;
+     _c2i_unverified_entry = c2i_unverified_entry;
+     _c2i_no_clinit_check_entry = c2i_no_clinit_check_entry;
+     _linked = linked;
+   }
+ 
    address get_i2c_entry()                  const { return _i2c_entry; }
    address get_c2i_entry()                  const { return _c2i_entry; }
    address get_c2i_unverified_entry()       const { return _c2i_unverified_entry; }
    address get_c2i_no_clinit_check_entry()  const { return _c2i_no_clinit_check_entry; }
  
+   bool is_linked() const { return _linked; }
    address base_address();
    void relocate(address new_base);
  
    AdapterFingerPrint* fingerprint() const { return _fingerprint; }
  

@@ -717,45 +754,80 @@
    bool compare_code(AdapterHandlerEntry* other);
  #endif
  
    //virtual void print_on(outputStream* st) const;  DO NOT USE
    void print_adapter_on(outputStream* st) const;
+ 
+   void metaspace_pointers_do(MetaspaceClosure* it);
+   int size() const {return (int)heap_word_size(sizeof(AdapterHandlerEntry)); }
+   MetaspaceObj::Type type() const { return AdapterHandlerEntryType; }
+ 
+   void remove_unshareable_info() NOT_CDS_RETURN;
+   void restore_unshareable_info(TRAPS) NOT_CDS_RETURN;
  };
  
+ #if INCLUDE_CDS
+ class ArchivedAdapterTable;
+ #endif // INCLUDE_CDS
+ 
  class AdapterHandlerLibrary: public AllStatic {
    friend class SharedRuntime;
   private:
    static BufferBlob* _buffer; // the temporary code buffer in CodeCache
    static AdapterHandlerEntry* _abstract_method_handler;
    static AdapterHandlerEntry* _no_arg_handler;
    static AdapterHandlerEntry* _int_arg_handler;
    static AdapterHandlerEntry* _obj_arg_handler;
    static AdapterHandlerEntry* _obj_int_arg_handler;
    static AdapterHandlerEntry* _obj_obj_arg_handler;
- 
+ #if INCLUDE_CDS
+   static ArchivedAdapterTable _archived_adapter_handler_table;
+ #endif // INCLUDE_CDS
    static BufferBlob* buffer_blob();
    static void initialize();
+   static AdapterHandlerEntry* create_simple_adapter(AdapterBlob*& new_adapter,
+                                                     int total_args_passed,
+                                                     BasicType* sig_bt);
+   static AdapterHandlerEntry* get_simple_adapter(const methodHandle& method);
+   static bool lookup_aot_cache(AdapterHandlerEntry* handler, CodeBuffer* buffer);
    static AdapterHandlerEntry* create_adapter(AdapterBlob*& new_adapter,
+                                              AdapterFingerPrint* fingerprint,
                                               int total_args_passed,
                                               BasicType* sig_bt,
-                                              bool allocate_code_blob);
-   static AdapterHandlerEntry* get_simple_adapter(const methodHandle& method);
+                                              bool is_transient);
+ #ifndef PRODUCT
+   static void print_adapter_handler_info(AdapterHandlerEntry* handler, AdapterBlob* adapter_blob);
+ #endif // PRODUCT
   public:
  
    static AdapterHandlerEntry* new_entry(AdapterFingerPrint* fingerprint,
-                                         address i2c_entry,
-                                         address c2i_entry,
-                                         address c2i_unverified_entry,
+                                         address i2c_entry = nullptr,
+                                         address c2i_entry = nullptr,
+                                         address c2i_unverified_entry = nullptr,
                                          address c2i_no_clinit_check_entry = nullptr);
    static void create_native_wrapper(const methodHandle& method);
    static AdapterHandlerEntry* get_adapter(const methodHandle& method);
+   static AdapterHandlerEntry* lookup(AdapterFingerPrint* fp);
+   static bool generate_adapter_code(AdapterBlob*& adapter_blob,
+                                     AdapterHandlerEntry* handler,
+                                     int total_args_passed,
+                                     BasicType* sig_bt,
+                                     bool is_transient);
  
    static void print_handler(const CodeBlob* b) { print_handler_on(tty, b); }
    static void print_handler_on(outputStream* st, const CodeBlob* b);
    static bool contains(const CodeBlob* b);
+   static const char* name(AdapterFingerPrint* fingerprint);
+   static uint32_t id(AdapterFingerPrint* fingerprint);
  #ifndef PRODUCT
-   static void print_statistics();
+   static void print_statistics_on(outputStream* st);
  #endif // PRODUCT
  
+   static bool is_abstract_method_adapter(AdapterHandlerEntry* adapter);
+ 
+   static bool link_adapter_handler(AdapterHandlerEntry* handler, AdapterBlob*& adapter_blob) NOT_CDS_RETURN_(false);
+   static size_t estimate_size_for_archive() NOT_CDS_RETURN_(0);
+   static void archive_adapter_table() NOT_CDS_RETURN;
+   static void serialize_shared_table_header(SerializeClosure* soc) NOT_CDS_RETURN;
  };
  
  #endif // SHARE_RUNTIME_SHAREDRUNTIME_HPP
< prev index next >