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  */
  25 
  26 class SharkState;
  27 
  28 class SharkBlock : public SharkTargetInvariants {
  29  protected:
  30   SharkBlock(const SharkTargetInvariants* parent)
  31     : SharkTargetInvariants(parent),
  32       _iter(target()),
  33       _current_state(NULL) {}
  34 
  35   SharkBlock(const SharkCompileInvariants* parent, ciMethod* target)
  36     : SharkTargetInvariants(parent, target),
  37       _iter(target),
  38       _current_state(NULL) {}
  39 
  40  private:
  41   ciBytecodeStream _iter;
  42   SharkState*      _current_state;
  43 
  44  public:
  45   ciBytecodeStream* iter() {
  46     return &_iter;
  47   }
  48   Bytecodes::Code bc() {
  49     return iter()->cur_bc();
  50   }
  51   int bci() {
  52     return iter()->cur_bci();
  53   }
  54 
  55   // Entry state
  56  protected:
  57   virtual SharkState* entry_state();
  58 
  59   // Current state
  60  private:
  61   SharkState* initial_current_state();
  62 
  63  public:
  64   SharkState* current_state() {
  65     if (_current_state == NULL)
  66       set_current_state(initial_current_state());
  67     return _current_state;
  68   }
  69 
  70  protected:
  71   void set_current_state(SharkState* current_state) {
  72     _current_state = current_state;
  73   }
  74 
  75   // Local variables
  76  protected:
  77   SharkValue* local(int index) {
  78     SharkValue *value = current_state()->local(index);
  79     assert(value != NULL, "shouldn't be");
  80     assert(value->is_one_word() ||
  81            (index + 1 < max_locals() &&
  82             current_state()->local(index + 1) == NULL), "should be");
  83     return value;
  84   }
  85   void set_local(int index, SharkValue* value) {
  86     assert(value != NULL, "shouldn't be");
  87     current_state()->set_local(index, value);
  88     if (value->is_two_word())
  89       current_state()->set_local(index + 1, NULL);
  90   }
  91 
  92   // Expression stack (raw)
  93  protected:
  94   void xpush(SharkValue* value) {
  95     current_state()->push(value);
  96   }
  97   SharkValue* xpop() {
  98     return current_state()->pop();
  99   }
 100   SharkValue* xstack(int slot) {
 101     SharkValue *value = current_state()->stack(slot);
 102     assert(value != NULL, "shouldn't be");
 103     assert(value->is_one_word() ||
 104            (slot > 0 &&
 105             current_state()->stack(slot - 1) == NULL), "should be");
 106     return value;
 107   }
 108   int xstack_depth() {
 109     return current_state()->stack_depth();
 110   }
 111 
 112   // Expression stack (cooked)
 113  protected:
 114   void push(SharkValue* value) {
 115     assert(value != NULL, "shouldn't be");
 116     xpush(value);
 117     if (value->is_two_word())
 118       xpush(NULL);
 119   }
 120   SharkValue* pop() {
 121     int size = current_state()->stack(0) == NULL ? 2 : 1;
 122     if (size == 2)
 123       xpop();
 124     SharkValue *value = xpop();
 125     assert(value && value->size() == size, "should be");
 126     return value;
 127   }
 128   SharkValue* pop_result(BasicType type) {
 129     SharkValue *result = pop();
 130 
 131 #ifdef ASSERT
 132     switch (result->basic_type()) {
 133     case T_BOOLEAN:
 134     case T_BYTE:
 135     case T_CHAR:
 136     case T_SHORT:
 137       assert(type == T_INT, "type mismatch");
 138       break;
 139 
 140     case T_ARRAY:
 141       assert(type == T_OBJECT, "type mismatch");
 142       break;
 143 
 144     default:
 145       assert(result->basic_type() == type, "type mismatch");
 146     }
 147 #endif // ASSERT
 148 
 149     return result;
 150   }
 151 
 152   // Code generation
 153  public:
 154   virtual void emit_IR();
 155 
 156  protected:
 157   void parse_bytecode(int start, int limit);
 158 
 159   // Helpers
 160  protected:
 161   virtual void do_zero_check(SharkValue* value);
 162 
 163   // Zero checking
 164  protected:
 165   void check_null(SharkValue* object) {
 166     zero_check(object);
 167   }
 168   void check_divide_by_zero(SharkValue* value) {
 169     zero_check(value);
 170   }
 171  private:
 172   void zero_check(SharkValue* value) {
 173     if (!value->zero_checked())
 174       do_zero_check(value);
 175   }
 176 
 177   // Safepoints
 178  protected:
 179   virtual void maybe_add_backedge_safepoint();
 180 
 181   // Traps
 182  protected:
 183   virtual bool has_trap();
 184   virtual int  trap_request();
 185   virtual int  trap_bci();
 186   virtual void do_trap(int trap_request);
 187 
 188   // arraylength
 189  protected:
 190   virtual void do_arraylength();
 191 
 192   // *aload and *astore
 193  protected:
 194   virtual void do_aload(BasicType basic_type);
 195   virtual void do_astore(BasicType basic_type);
 196 
 197   // *div and *rem
 198  private:
 199   void do_idiv() {
 200     do_div_or_rem(false, false);
 201   }
 202   void do_irem() {
 203     do_div_or_rem(false, true);
 204   }
 205   void do_ldiv() {
 206     do_div_or_rem(true, false);
 207   }
 208   void do_lrem() {
 209     do_div_or_rem(true, true);
 210   }
 211   void do_div_or_rem(bool is_long, bool is_rem);
 212 
 213   // get* and put*
 214  private:
 215   void do_getstatic() {
 216     do_field_access(true, false);
 217   }
 218   void do_getfield() {
 219     do_field_access(true, true);
 220   }
 221   void do_putstatic() {
 222     do_field_access(false, false);
 223   }
 224   void do_putfield() {
 225     do_field_access(false, true);
 226   }
 227   void do_field_access(bool is_get, bool is_field);
 228 
 229   // lcmp and [fd]cmp[lg]
 230  private:
 231   void do_lcmp();
 232   void do_fcmp(bool is_double, bool unordered_is_greater);
 233 
 234   // *return and athrow
 235  protected:
 236   virtual void do_return(BasicType type);
 237   virtual void do_athrow();
 238 
 239   // goto*
 240  protected:
 241   virtual void do_goto();
 242 
 243   // jsr* and ret
 244  protected:
 245   virtual void do_jsr();
 246   virtual void do_ret();
 247 
 248   // if*
 249  protected:
 250   virtual void do_if(llvm::ICmpInst::Predicate p, SharkValue* b, SharkValue* a);
 251 
 252   // *switch
 253  protected:
 254   int switch_default_dest();
 255   int switch_table_length();
 256   int switch_key(int i);
 257   int switch_dest(int i);
 258 
 259   virtual void do_switch();
 260 
 261   // invoke*
 262  protected:
 263   virtual void do_call();
 264 
 265   // checkcast and instanceof
 266  protected:
 267   virtual void do_instance_check();
 268   virtual bool maybe_do_instanceof_if();
 269 
 270   // new and *newarray
 271  protected:
 272   virtual void do_new();
 273   virtual void do_newarray();
 274   virtual void do_anewarray();
 275   virtual void do_multianewarray();
 276 
 277   // monitorenter and monitorexit
 278  protected:
 279   virtual void do_monitorenter();
 280   virtual void do_monitorexit();
 281 };