src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp

changeset 1079
c517646eef23
parent 791
1ee8caae33af
child 1100
c89f86385056
     1.1 --- a/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Fri Mar 13 11:35:17 2009 -0700
     1.2 +++ b/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Fri Mar 13 18:39:22 2009 -0700
     1.3 @@ -2393,23 +2393,11 @@
     1.4  
     1.5      // get instance klass
     1.6      load(k_RInfo, objArrayKlass::element_klass_offset_in_bytes() + sizeof(oopDesc), k_RInfo, T_OBJECT, NULL);
     1.7 -    // get super_check_offset
     1.8 -    load(k_RInfo, sizeof(oopDesc) + Klass::super_check_offset_offset_in_bytes(), Rtmp1, T_INT, NULL);
     1.9 -    // See if we get an immediate positive hit
    1.10 -    __ ld_ptr(klass_RInfo, Rtmp1, FrameMap::O7_oop_opr->as_register());
    1.11 -    __ cmp(k_RInfo, O7);
    1.12 -    __ br(Assembler::equal, false, Assembler::pn, done);
    1.13 -    __ delayed()->nop();
    1.14 -    // check for immediate negative hit
    1.15 -    __ cmp(Rtmp1, sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes());
    1.16 -    __ br(Assembler::notEqual, false, Assembler::pn, *stub->entry());
    1.17 -    __ delayed()->nop();
    1.18 -    // check for self
    1.19 -    __ cmp(klass_RInfo, k_RInfo);
    1.20 -    __ br(Assembler::equal, false, Assembler::pn, done);
    1.21 -    __ delayed()->nop();
    1.22 -
    1.23 -    // assert(sub.is_same(FrameMap::G3_RInfo) && super.is_same(FrameMap::G1_RInfo), "incorrect call setup");
    1.24 +    // perform the fast part of the checking logic
    1.25 +    __ check_klass_subtype_fast_path(klass_RInfo, k_RInfo, Rtmp1, O7, &done, stub->entry(), NULL);
    1.26 +
    1.27 +    // call out-of-line instance of __ check_klass_subtype_slow_path(...):
    1.28 +    assert(klass_RInfo == G3 && k_RInfo == G1, "incorrect call setup");
    1.29      __ call(Runtime1::entry_for(Runtime1::slow_subtype_check_id), relocInfo::runtime_call_type);
    1.30      __ delayed()->nop();
    1.31      __ cmp(G3, 0);
    1.32 @@ -2493,58 +2481,30 @@
    1.33        __ delayed()->nop();
    1.34        __ bind(done);
    1.35      } else {
    1.36 +      bool need_slow_path = true;
    1.37        if (k->is_loaded()) {
    1.38 -        load(klass_RInfo, k->super_check_offset(), Rtmp1, T_OBJECT, NULL);
    1.39 -
    1.40 -        if (sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes() != k->super_check_offset()) {
    1.41 -          // See if we get an immediate positive hit
    1.42 -          __ cmp(Rtmp1, k_RInfo );
    1.43 -          __ br(Assembler::notEqual, false, Assembler::pn, *stub->entry());
    1.44 -          __ delayed()->nop();
    1.45 -        } else {
    1.46 -          // See if we get an immediate positive hit
    1.47 -          assert_different_registers(Rtmp1, k_RInfo, klass_RInfo);
    1.48 -          __ cmp(Rtmp1, k_RInfo );
    1.49 -          __ br(Assembler::equal, false, Assembler::pn, done);
    1.50 -          // check for self
    1.51 -          __ delayed()->cmp(klass_RInfo, k_RInfo);
    1.52 -          __ br(Assembler::equal, false, Assembler::pn, done);
    1.53 -          __ delayed()->nop();
    1.54 -
    1.55 -          // assert(sub.is_same(FrameMap::G3_RInfo) && super.is_same(FrameMap::G1_RInfo), "incorrect call setup");
    1.56 -          __ call(Runtime1::entry_for(Runtime1::slow_subtype_check_id), relocInfo::runtime_call_type);
    1.57 -          __ delayed()->nop();
    1.58 -          __ cmp(G3, 0);
    1.59 -          __ br(Assembler::equal, false, Assembler::pn, *stub->entry());
    1.60 -          __ delayed()->nop();
    1.61 -        }
    1.62 -        __ bind(done);
    1.63 +        if (k->super_check_offset() != sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes())
    1.64 +          need_slow_path = false;
    1.65 +        // perform the fast part of the checking logic
    1.66 +        __ check_klass_subtype_fast_path(klass_RInfo, k_RInfo, Rtmp1, noreg,
    1.67 +                                         (need_slow_path ? &done : NULL),
    1.68 +                                         stub->entry(), NULL,
    1.69 +                                         RegisterConstant(k->super_check_offset()));
    1.70        } else {
    1.71 -        assert_different_registers(Rtmp1, klass_RInfo, k_RInfo);
    1.72 -
    1.73 -        load(k_RInfo, sizeof(oopDesc) + Klass::super_check_offset_offset_in_bytes(), Rtmp1, T_INT, NULL);
    1.74 -        // See if we get an immediate positive hit
    1.75 -        load(klass_RInfo, Rtmp1, FrameMap::O7_oop_opr, T_OBJECT);
    1.76 -        __ cmp(k_RInfo, O7);
    1.77 -        __ br(Assembler::equal, false, Assembler::pn, done);
    1.78 -        __ delayed()->nop();
    1.79 -        // check for immediate negative hit
    1.80 -        __ cmp(Rtmp1, sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes());
    1.81 -        __ br(Assembler::notEqual, false, Assembler::pn, *stub->entry());
    1.82 -        // check for self
    1.83 -        __ delayed()->cmp(klass_RInfo, k_RInfo);
    1.84 -        __ br(Assembler::equal, false, Assembler::pn, done);
    1.85 -        __ delayed()->nop();
    1.86 -
    1.87 -        // assert(sub.is_same(FrameMap::G3_RInfo) && super.is_same(FrameMap::G1_RInfo), "incorrect call setup");
    1.88 +        // perform the fast part of the checking logic
    1.89 +        __ check_klass_subtype_fast_path(klass_RInfo, k_RInfo, Rtmp1, O7,
    1.90 +                                         &done, stub->entry(), NULL);
    1.91 +      }
    1.92 +      if (need_slow_path) {
    1.93 +        // call out-of-line instance of __ check_klass_subtype_slow_path(...):
    1.94 +        assert(klass_RInfo == G3 && k_RInfo == G1, "incorrect call setup");
    1.95          __ call(Runtime1::entry_for(Runtime1::slow_subtype_check_id), relocInfo::runtime_call_type);
    1.96          __ delayed()->nop();
    1.97          __ cmp(G3, 0);
    1.98          __ br(Assembler::equal, false, Assembler::pn, *stub->entry());
    1.99          __ delayed()->nop();
   1.100 -        __ bind(done);
   1.101        }
   1.102 -
   1.103 +      __ bind(done);
   1.104      }
   1.105      __ mov(obj, dst);
   1.106    } else if (code == lir_instanceof) {
   1.107 @@ -2582,58 +2542,32 @@
   1.108        __ set(0, dst);
   1.109        __ bind(done);
   1.110      } else {
   1.111 +      bool need_slow_path = true;
   1.112        if (k->is_loaded()) {
   1.113 -        assert_different_registers(Rtmp1, klass_RInfo, k_RInfo);
   1.114 -        load(klass_RInfo, k->super_check_offset(), Rtmp1, T_OBJECT, NULL);
   1.115 -
   1.116 -        if (sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes() != k->super_check_offset()) {
   1.117 -          // See if we get an immediate positive hit
   1.118 -          __ cmp(Rtmp1, k_RInfo );
   1.119 -          __ br(Assembler::equal, true, Assembler::pt, done);
   1.120 -          __ delayed()->set(1, dst);
   1.121 -          __ set(0, dst);
   1.122 -          __ bind(done);
   1.123 -        } else {
   1.124 -          // See if we get an immediate positive hit
   1.125 -          assert_different_registers(Rtmp1, k_RInfo, klass_RInfo);
   1.126 -          __ cmp(Rtmp1, k_RInfo );
   1.127 -          __ br(Assembler::equal, true, Assembler::pt, done);
   1.128 -          __ delayed()->set(1, dst);
   1.129 -          // check for self
   1.130 -          __ cmp(klass_RInfo, k_RInfo);
   1.131 -          __ br(Assembler::equal, true, Assembler::pt, done);
   1.132 -          __ delayed()->set(1, dst);
   1.133 -
   1.134 -          // assert(sub.is_same(FrameMap::G3_RInfo) && super.is_same(FrameMap::G1_RInfo), "incorrect call setup");
   1.135 -          __ call(Runtime1::entry_for(Runtime1::slow_subtype_check_id), relocInfo::runtime_call_type);
   1.136 -          __ delayed()->nop();
   1.137 -          __ mov(G3, dst);
   1.138 -          __ bind(done);
   1.139 -        }
   1.140 +        if (k->super_check_offset() != sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes())
   1.141 +          need_slow_path = false;
   1.142 +        // perform the fast part of the checking logic
   1.143 +        __ check_klass_subtype_fast_path(klass_RInfo, k_RInfo, O7, noreg,
   1.144 +                                         (need_slow_path ? &done : NULL),
   1.145 +                                         (need_slow_path ? &done : NULL), NULL,
   1.146 +                                         RegisterConstant(k->super_check_offset()),
   1.147 +                                         dst);
   1.148        } else {
   1.149          assert(dst != klass_RInfo && dst != k_RInfo, "need 3 registers");
   1.150 -
   1.151 -        load(k_RInfo, sizeof(oopDesc) + Klass::super_check_offset_offset_in_bytes(), dst, T_INT, NULL);
   1.152 -        // See if we get an immediate positive hit
   1.153 -        load(klass_RInfo, dst, FrameMap::O7_oop_opr, T_OBJECT);
   1.154 -        __ cmp(k_RInfo, O7);
   1.155 -        __ br(Assembler::equal, true, Assembler::pt, done);
   1.156 -        __ delayed()->set(1, dst);
   1.157 -        // check for immediate negative hit
   1.158 -        __ cmp(dst, sizeof(oopDesc) + Klass::secondary_super_cache_offset_in_bytes());
   1.159 -        __ br(Assembler::notEqual, true, Assembler::pt, done);
   1.160 -        __ delayed()->set(0, dst);
   1.161 -        // check for self
   1.162 -        __ cmp(klass_RInfo, k_RInfo);
   1.163 -        __ br(Assembler::equal, true, Assembler::pt, done);
   1.164 -        __ delayed()->set(1, dst);
   1.165 -
   1.166 -        // assert(sub.is_same(FrameMap::G3_RInfo) && super.is_same(FrameMap::G1_RInfo), "incorrect call setup");
   1.167 +        // perform the fast part of the checking logic
   1.168 +        __ check_klass_subtype_fast_path(klass_RInfo, k_RInfo, O7, dst,
   1.169 +                                         &done, &done, NULL,
   1.170 +                                         RegisterConstant(-1),
   1.171 +                                         dst);
   1.172 +      }
   1.173 +      if (need_slow_path) {
   1.174 +        // call out-of-line instance of __ check_klass_subtype_slow_path(...):
   1.175 +        assert(klass_RInfo == G3 && k_RInfo == G1, "incorrect call setup");
   1.176          __ call(Runtime1::entry_for(Runtime1::slow_subtype_check_id), relocInfo::runtime_call_type);
   1.177          __ delayed()->nop();
   1.178          __ mov(G3, dst);
   1.179 -        __ bind(done);
   1.180        }
   1.181 +      __ bind(done);
   1.182      }
   1.183    } else {
   1.184      ShouldNotReachHere();

mercurial