src/share/vm/shark/sharkCacheDecache.hpp

Wed, 11 Aug 2010 05:51:21 -0700

author
twisti
date
Wed, 11 Aug 2010 05:51:21 -0700
changeset 2047
d2ede61b7a12
child 2314
f95d63e2154a
permissions
-rw-r--r--

6976186: integrate Shark HotSpot changes
Summary: Shark is a JIT compiler for Zero that uses the LLVM compiler infrastructure.
Reviewed-by: kvn, twisti
Contributed-by: Gary Benson <gbenson@redhat.com>

     1 /*
     2  * Copyright (c) 1999, 2007, Oracle and/or its affiliates. All rights reserved.
     3  * Copyright 2008, 2009 Red Hat, Inc.
     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  */
    26 // Class hierarchy:
    27 // - SharkStateScanner
    28 //   - SharkCacherDecacher
    29 //     - SharkDecacher
    30 //       - SharkJavaCallDecacher
    31 //       - SharkVMCallDecacher
    32 //       - SharkTrapDecacher
    33 //     - SharkCacher
    34 //       - SharkJavaCallCacher
    35 //       - SharkVMCallCacher
    36 //       - SharkFunctionEntryCacher
    37 //         - SharkNormalEntryCacher
    38 //         - SharkOSREntryCacher
    40 class SharkCacherDecacher : public SharkStateScanner {
    41  protected:
    42   SharkCacherDecacher(SharkFunction* function)
    43     : SharkStateScanner(function) {}
    45   // Helper
    46  protected:
    47   static int adjusted_offset(SharkValue* value, int offset) {
    48     if (value->is_two_word())
    49       offset--;
    50     return offset;
    51   }
    52 };
    54 class SharkDecacher : public SharkCacherDecacher {
    55  protected:
    56   SharkDecacher(SharkFunction* function, int bci)
    57     : SharkCacherDecacher(function), _bci(bci) {}
    59  private:
    60   int _bci;
    62  protected:
    63   int bci() const {
    64     return _bci;
    65   }
    67  private:
    68   int                           _pc_offset;
    69   OopMap*                       _oopmap;
    70   GrowableArray<ScopeValue*>*   _exparray;
    71   GrowableArray<MonitorValue*>* _monarray;
    72   GrowableArray<ScopeValue*>*   _locarray;
    74  private:
    75   int pc_offset() const {
    76     return _pc_offset;
    77   }
    78   OopMap* oopmap() const {
    79     return _oopmap;
    80   }
    81   GrowableArray<ScopeValue*>* exparray() const {
    82     return _exparray;
    83   }
    84   GrowableArray<MonitorValue*>* monarray() const {
    85     return _monarray;
    86   }
    87   GrowableArray<ScopeValue*>* locarray() const {
    88     return _locarray;
    89   }
    91   // Callbacks
    92  protected:
    93   void start_frame();
    95   void start_stack(int stack_depth);
    96   void process_stack_slot(int index, SharkValue** value, int offset);
    98   void start_monitors(int num_monitors);
    99   void process_monitor(int index, int box_offset, int obj_offset);
   101   void process_oop_tmp_slot(llvm::Value** value, int offset);
   102   void process_method_slot(llvm::Value** value, int offset);
   103   void process_pc_slot(int offset);
   105   void start_locals();
   106   void process_local_slot(int index, SharkValue** value, int offset);
   108   void end_frame();
   110   // oopmap and debuginfo helpers
   111  private:
   112   static int oopmap_slot_munge(int offset) {
   113     return SharkStack::oopmap_slot_munge(offset);
   114   }
   115   static VMReg slot2reg(int offset) {
   116     return SharkStack::slot2reg(offset);
   117   }
   118   static Location slot2loc(int offset, Location::Type type) {
   119     return Location::new_stk_loc(type, offset * wordSize);
   120   }
   121   static LocationValue* slot2lv(int offset, Location::Type type) {
   122     return new LocationValue(slot2loc(offset, type));
   123   }
   124   static Location::Type location_type(SharkValue** addr, bool maybe_two_word) {
   125     // low addresses this end
   126     //                           Type       32-bit    64-bit
   127     //   ----------------------------------------------------
   128     //   stack[0]    local[3]    jobject    oop       oop
   129     //   stack[1]    local[2]    NULL       normal    lng
   130     //   stack[2]    local[1]    jlong      normal    invalid
   131     //   stack[3]    local[0]    jint       normal    normal
   132     //
   133     // high addresses this end
   135     SharkValue *value = *addr;
   136     if (value) {
   137       if (value->is_jobject())
   138         return Location::oop;
   139 #ifdef _LP64
   140       if (value->is_two_word())
   141         return Location::invalid;
   142 #endif // _LP64
   143       return Location::normal;
   144     }
   145     else {
   146       if (maybe_two_word) {
   147         value = *(addr - 1);
   148         if (value && value->is_two_word()) {
   149 #ifdef _LP64
   150           if (value->is_jlong())
   151             return Location::lng;
   152           if (value->is_jdouble())
   153             return Location::dbl;
   154           ShouldNotReachHere();
   155 #else
   156           return Location::normal;
   157 #endif // _LP64
   158         }
   159       }
   160       return Location::invalid;
   161     }
   162   }
   164   // Stack slot helpers
   165  protected:
   166   virtual bool stack_slot_needs_write(int index, SharkValue* value) = 0;
   167   virtual bool stack_slot_needs_oopmap(int index, SharkValue* value) = 0;
   168   virtual bool stack_slot_needs_debuginfo(int index, SharkValue* value) = 0;
   170   static Location::Type stack_location_type(int index, SharkValue** addr) {
   171     return location_type(addr, *addr == NULL);
   172   }
   174   // Local slot helpers
   175  protected:
   176   virtual bool local_slot_needs_write(int index, SharkValue* value) = 0;
   177   virtual bool local_slot_needs_oopmap(int index, SharkValue* value) = 0;
   178   virtual bool local_slot_needs_debuginfo(int index, SharkValue* value) = 0;
   180   static Location::Type local_location_type(int index, SharkValue** addr) {
   181     return location_type(addr, index > 0);
   182   }
   184   // Writer helper
   185  protected:
   186   void write_value_to_frame(const llvm::Type* type,
   187                             llvm::Value*      value,
   188                             int               offset);
   189 };
   191 class SharkJavaCallDecacher : public SharkDecacher {
   192  public:
   193   SharkJavaCallDecacher(SharkFunction* function, int bci, ciMethod* callee)
   194     : SharkDecacher(function, bci), _callee(callee) {}
   196  private:
   197   ciMethod* _callee;
   199  protected:
   200   ciMethod* callee() const {
   201     return _callee;
   202   }
   204   // Stack slot helpers
   205  protected:
   206   bool stack_slot_needs_write(int index, SharkValue* value) {
   207     return value && (index < callee()->arg_size() || value->is_jobject());
   208   }
   209   bool stack_slot_needs_oopmap(int index, SharkValue* value) {
   210     return value && value->is_jobject() && index >= callee()->arg_size();
   211   }
   212   bool stack_slot_needs_debuginfo(int index, SharkValue* value) {
   213     return index >= callee()->arg_size();
   214   }
   216   // Local slot helpers
   217  protected:
   218   bool local_slot_needs_write(int index, SharkValue* value) {
   219     return value && value->is_jobject();
   220   }
   221   bool local_slot_needs_oopmap(int index, SharkValue* value) {
   222     return value && value->is_jobject();
   223   }
   224   bool local_slot_needs_debuginfo(int index, SharkValue* value) {
   225     return true;
   226   }
   227 };
   229 class SharkVMCallDecacher : public SharkDecacher {
   230  public:
   231   SharkVMCallDecacher(SharkFunction* function, int bci)
   232     : SharkDecacher(function, bci) {}
   234   // Stack slot helpers
   235  protected:
   236   bool stack_slot_needs_write(int index, SharkValue* value) {
   237     return value && value->is_jobject();
   238   }
   239   bool stack_slot_needs_oopmap(int index, SharkValue* value) {
   240     return value && value->is_jobject();
   241   }
   242   bool stack_slot_needs_debuginfo(int index, SharkValue* value) {
   243     return true;
   244   }
   246   // Local slot helpers
   247  protected:
   248   bool local_slot_needs_write(int index, SharkValue* value) {
   249     return value && value->is_jobject();
   250   }
   251   bool local_slot_needs_oopmap(int index, SharkValue* value) {
   252     return value && value->is_jobject();
   253   }
   254   bool local_slot_needs_debuginfo(int index, SharkValue* value) {
   255     return true;
   256   }
   257 };
   259 class SharkTrapDecacher : public SharkDecacher {
   260  public:
   261   SharkTrapDecacher(SharkFunction* function, int bci)
   262     : SharkDecacher(function, bci) {}
   264   // Stack slot helpers
   265  protected:
   266   bool stack_slot_needs_write(int index, SharkValue* value) {
   267     return value != NULL;
   268   }
   269   bool stack_slot_needs_oopmap(int index, SharkValue* value) {
   270     return value && value->is_jobject();
   271   }
   272   bool stack_slot_needs_debuginfo(int index, SharkValue* value) {
   273     return true;
   274   }
   276   // Local slot helpers
   277  protected:
   278   bool local_slot_needs_write(int index, SharkValue* value) {
   279     return value != NULL;
   280   }
   281   bool local_slot_needs_oopmap(int index, SharkValue* value) {
   282     return value && value->is_jobject();
   283   }
   284   bool local_slot_needs_debuginfo(int index, SharkValue* value) {
   285     return true;
   286   }
   287 };
   289 class SharkCacher : public SharkCacherDecacher {
   290  protected:
   291   SharkCacher(SharkFunction* function)
   292     : SharkCacherDecacher(function) {}
   294   // Callbacks
   295  protected:
   296   void process_stack_slot(int index, SharkValue** value, int offset);
   298   void process_oop_tmp_slot(llvm::Value** value, int offset);
   299   virtual void process_method_slot(llvm::Value** value, int offset);
   301   virtual void process_local_slot(int index, SharkValue** value, int offset);
   303   // Stack slot helper
   304  protected:
   305   virtual bool stack_slot_needs_read(int index, SharkValue* value) = 0;
   307   // Local slot helper
   308  protected:
   309   virtual bool local_slot_needs_read(int index, SharkValue* value) {
   310     return value && value->is_jobject();
   311   }
   313   // Writer helper
   314  protected:
   315   llvm::Value* read_value_from_frame(const llvm::Type* type, int offset);
   316 };
   318 class SharkJavaCallCacher : public SharkCacher {
   319  public:
   320   SharkJavaCallCacher(SharkFunction* function, ciMethod* callee)
   321     : SharkCacher(function), _callee(callee) {}
   323  private:
   324   ciMethod* _callee;
   326  protected:
   327   ciMethod* callee() const {
   328     return _callee;
   329   }
   331   // Stack slot helper
   332  protected:
   333   bool stack_slot_needs_read(int index, SharkValue* value) {
   334     return value && (index < callee()->return_type()->size() ||
   335                      value->is_jobject());
   336   }
   337 };
   339 class SharkVMCallCacher : public SharkCacher {
   340  public:
   341   SharkVMCallCacher(SharkFunction* function)
   342     : SharkCacher(function) {}
   344   // Stack slot helper
   345  protected:
   346   bool stack_slot_needs_read(int index, SharkValue* value) {
   347     return value && value->is_jobject();
   348   }
   349 };
   351 class SharkFunctionEntryCacher : public SharkCacher {
   352  public:
   353   SharkFunctionEntryCacher(SharkFunction* function, llvm::Value* method)
   354     : SharkCacher(function), _method(method) {}
   356  private:
   357   llvm::Value* _method;
   359  private:
   360   llvm::Value* method() const {
   361     return _method;
   362   }
   364   // Method slot callback
   365  protected:
   366   void process_method_slot(llvm::Value** value, int offset);
   368   // Stack slot helper
   369  protected:
   370   bool stack_slot_needs_read(int index, SharkValue* value) {
   371     ShouldNotReachHere(); // entry block shouldn't have stack
   372   }
   374   // Local slot helper
   375  protected:
   376   bool local_slot_needs_read(int index, SharkValue* value) {
   377     return value != NULL;
   378   }
   379 };
   381 class SharkNormalEntryCacher : public SharkFunctionEntryCacher {
   382  public:
   383   SharkNormalEntryCacher(SharkFunction* function, llvm::Value* method)
   384     : SharkFunctionEntryCacher(function, method) {}
   385 };
   387 class SharkOSREntryCacher : public SharkFunctionEntryCacher {
   388  public:
   389   SharkOSREntryCacher(SharkFunction* function,
   390                       llvm::Value*   method,
   391                       llvm::Value*   osr_buf)
   392     : SharkFunctionEntryCacher(function, method),
   393       _osr_buf(
   394         builder()->CreateBitCast(
   395           osr_buf,
   396           llvm::PointerType::getUnqual(
   397             llvm::ArrayType::get(
   398               SharkType::intptr_type(),
   399               max_locals() + max_monitors() * 2)))) {}
   401  private:
   402   llvm::Value* _osr_buf;
   404  private:
   405   llvm::Value* osr_buf() const {
   406     return _osr_buf;
   407   }
   409   // Callbacks
   410  protected:
   411   void process_monitor(int index, int box_offset, int obj_offset);
   412   void process_local_slot(int index, SharkValue** value, int offset);
   414   // Helper
   415  private:
   416   llvm::Value* CreateAddressOfOSRBufEntry(int offset, const llvm::Type* type);
   417 };

mercurial