1.1 --- a/src/share/vm/opto/type.cpp Fri Sep 13 07:57:13 2013 +0200 1.2 +++ b/src/share/vm/opto/type.cpp Mon Sep 16 09:41:03 2013 +0200 1.3 @@ -189,6 +189,38 @@ 1.4 } 1.5 1.6 1.7 +//-----------------------make_from_constant------------------------------------ 1.8 +const Type* Type::make_from_constant(ciConstant constant, 1.9 + bool require_constant, bool is_autobox_cache) { 1.10 + switch (constant.basic_type()) { 1.11 + case T_BOOLEAN: return TypeInt::make(constant.as_boolean()); 1.12 + case T_CHAR: return TypeInt::make(constant.as_char()); 1.13 + case T_BYTE: return TypeInt::make(constant.as_byte()); 1.14 + case T_SHORT: return TypeInt::make(constant.as_short()); 1.15 + case T_INT: return TypeInt::make(constant.as_int()); 1.16 + case T_LONG: return TypeLong::make(constant.as_long()); 1.17 + case T_FLOAT: return TypeF::make(constant.as_float()); 1.18 + case T_DOUBLE: return TypeD::make(constant.as_double()); 1.19 + case T_ARRAY: 1.20 + case T_OBJECT: 1.21 + { 1.22 + // cases: 1.23 + // can_be_constant = (oop not scavengable || ScavengeRootsInCode != 0) 1.24 + // should_be_constant = (oop not scavengable || ScavengeRootsInCode >= 2) 1.25 + // An oop is not scavengable if it is in the perm gen. 1.26 + ciObject* oop_constant = constant.as_object(); 1.27 + if (oop_constant->is_null_object()) { 1.28 + return Type::get_zero_type(T_OBJECT); 1.29 + } else if (require_constant || oop_constant->should_be_constant()) { 1.30 + return TypeOopPtr::make_from_constant(oop_constant, require_constant, is_autobox_cache); 1.31 + } 1.32 + } 1.33 + } 1.34 + // Fall through to failure 1.35 + return NULL; 1.36 +} 1.37 + 1.38 + 1.39 //------------------------------make------------------------------------------- 1.40 // Create a simple Type, with default empty symbol sets. Then hashcons it 1.41 // and look for an existing copy in the type dictionary. 1.42 @@ -1824,12 +1856,12 @@ 1.43 } 1.44 1.45 //------------------------------make------------------------------------------- 1.46 -const TypeAry *TypeAry::make( const Type *elem, const TypeInt *size) { 1.47 +const TypeAry* TypeAry::make(const Type* elem, const TypeInt* size, bool stable) { 1.48 if (UseCompressedOops && elem->isa_oopptr()) { 1.49 elem = elem->make_narrowoop(); 1.50 } 1.51 size = normalize_array_size(size); 1.52 - return (TypeAry*)(new TypeAry(elem,size))->hashcons(); 1.53 + return (TypeAry*)(new TypeAry(elem,size,stable))->hashcons(); 1.54 } 1.55 1.56 //------------------------------meet------------------------------------------- 1.57 @@ -1850,7 +1882,8 @@ 1.58 case Array: { // Meeting 2 arrays? 1.59 const TypeAry *a = t->is_ary(); 1.60 return TypeAry::make(_elem->meet(a->_elem), 1.61 - _size->xmeet(a->_size)->is_int()); 1.62 + _size->xmeet(a->_size)->is_int(), 1.63 + _stable & a->_stable); 1.64 } 1.65 case Top: 1.66 break; 1.67 @@ -1863,7 +1896,7 @@ 1.68 const Type *TypeAry::xdual() const { 1.69 const TypeInt* size_dual = _size->dual()->is_int(); 1.70 size_dual = normalize_array_size(size_dual); 1.71 - return new TypeAry( _elem->dual(), size_dual); 1.72 + return new TypeAry(_elem->dual(), size_dual, !_stable); 1.73 } 1.74 1.75 //------------------------------eq--------------------------------------------- 1.76 @@ -1871,13 +1904,14 @@ 1.77 bool TypeAry::eq( const Type *t ) const { 1.78 const TypeAry *a = (const TypeAry*)t; 1.79 return _elem == a->_elem && 1.80 + _stable == a->_stable && 1.81 _size == a->_size; 1.82 } 1.83 1.84 //------------------------------hash------------------------------------------- 1.85 // Type-specific hashing function. 1.86 int TypeAry::hash(void) const { 1.87 - return (intptr_t)_elem + (intptr_t)_size; 1.88 + return (intptr_t)_elem + (intptr_t)_size + (_stable ? 43 : 0); 1.89 } 1.90 1.91 //----------------------interface_vs_oop--------------------------------------- 1.92 @@ -1894,6 +1928,7 @@ 1.93 //------------------------------dump2------------------------------------------ 1.94 #ifndef PRODUCT 1.95 void TypeAry::dump2( Dict &d, uint depth, outputStream *st ) const { 1.96 + if (_stable) st->print("stable:"); 1.97 _elem->dump2(d, depth, st); 1.98 st->print("["); 1.99 _size->dump2(d, depth, st); 1.100 @@ -3457,11 +3492,39 @@ 1.101 assert(new_size != NULL, ""); 1.102 new_size = narrow_size_type(new_size); 1.103 if (new_size == size()) return this; 1.104 - const TypeAry* new_ary = TypeAry::make(elem(), new_size); 1.105 + const TypeAry* new_ary = TypeAry::make(elem(), new_size, is_stable()); 1.106 return make(ptr(), const_oop(), new_ary, klass(), klass_is_exact(), _offset, _instance_id); 1.107 } 1.108 1.109 1.110 +//------------------------------cast_to_stable--------------------------------- 1.111 +const TypeAryPtr* TypeAryPtr::cast_to_stable(bool stable, int stable_dimension) const { 1.112 + if (stable_dimension <= 0 || (stable_dimension == 1 && stable == this->is_stable())) 1.113 + return this; 1.114 + 1.115 + const Type* elem = this->elem(); 1.116 + const TypePtr* elem_ptr = elem->make_ptr(); 1.117 + 1.118 + if (stable_dimension > 1 && elem_ptr != NULL && elem_ptr->isa_aryptr()) { 1.119 + // If this is widened from a narrow oop, TypeAry::make will re-narrow it. 1.120 + elem = elem_ptr = elem_ptr->is_aryptr()->cast_to_stable(stable, stable_dimension - 1); 1.121 + } 1.122 + 1.123 + const TypeAry* new_ary = TypeAry::make(elem, size(), stable); 1.124 + 1.125 + return make(ptr(), const_oop(), new_ary, klass(), klass_is_exact(), _offset, _instance_id); 1.126 +} 1.127 + 1.128 +//-----------------------------stable_dimension-------------------------------- 1.129 +int TypeAryPtr::stable_dimension() const { 1.130 + if (!is_stable()) return 0; 1.131 + int dim = 1; 1.132 + const TypePtr* elem_ptr = elem()->make_ptr(); 1.133 + if (elem_ptr != NULL && elem_ptr->isa_aryptr()) 1.134 + dim += elem_ptr->is_aryptr()->stable_dimension(); 1.135 + return dim; 1.136 +} 1.137 + 1.138 //------------------------------eq--------------------------------------------- 1.139 // Structural equality check for Type representations 1.140 bool TypeAryPtr::eq( const Type *t ) const { 1.141 @@ -3570,7 +3633,7 @@ 1.142 // Something like byte[int+] meets char[int+]. 1.143 // This must fall to bottom, not (int[-128..65535])[int+]. 1.144 instance_id = InstanceBot; 1.145 - tary = TypeAry::make(Type::BOTTOM, tary->_size); 1.146 + tary = TypeAry::make(Type::BOTTOM, tary->_size, tary->_stable); 1.147 } 1.148 } else // Non integral arrays. 1.149 // Must fall to bottom if exact klasses in upper lattice 1.150 @@ -3584,7 +3647,7 @@ 1.151 (tap ->_klass_is_exact && !tap->klass()->is_subtype_of(klass())) || 1.152 // 'this' is exact and super or unrelated: 1.153 (this->_klass_is_exact && !klass()->is_subtype_of(tap->klass())))) { 1.154 - tary = TypeAry::make(Type::BOTTOM, tary->_size); 1.155 + tary = TypeAry::make(Type::BOTTOM, tary->_size, tary->_stable); 1.156 return make( NotNull, NULL, tary, lazy_klass, false, off, InstanceBot ); 1.157 } 1.158