839 uint LoadNode::size_of() const { return sizeof(*this); } |
839 uint LoadNode::size_of() const { return sizeof(*this); } |
840 uint LoadNode::cmp( const Node &n ) const |
840 uint LoadNode::cmp( const Node &n ) const |
841 { return !Type::cmp( _type, ((LoadNode&)n)._type ); } |
841 { return !Type::cmp( _type, ((LoadNode&)n)._type ); } |
842 const Type *LoadNode::bottom_type() const { return _type; } |
842 const Type *LoadNode::bottom_type() const { return _type; } |
843 uint LoadNode::ideal_reg() const { |
843 uint LoadNode::ideal_reg() const { |
844 return Matcher::base2reg[_type->base()]; |
844 return _type->ideal_reg(); |
845 } |
845 } |
846 |
846 |
847 #ifndef PRODUCT |
847 #ifndef PRODUCT |
848 void LoadNode::dump_spec(outputStream *st) const { |
848 void LoadNode::dump_spec(outputStream *st) const { |
849 MemNode::dump_spec(st); |
849 MemNode::dump_spec(st); |
1658 // (Folds up type checking code.) |
1658 // (Folds up type checking code.) |
1659 assert(Opcode() == Op_LoadI, "must load an int from _super_check_offset"); |
1659 assert(Opcode() == Op_LoadI, "must load an int from _super_check_offset"); |
1660 return TypeInt::make(klass->super_check_offset()); |
1660 return TypeInt::make(klass->super_check_offset()); |
1661 } |
1661 } |
1662 // Compute index into primary_supers array |
1662 // Compute index into primary_supers array |
1663 juint depth = (tkls->offset() - in_bytes(Klass::primary_supers_offset())) / sizeof(klassOop); |
1663 juint depth = (tkls->offset() - in_bytes(Klass::primary_supers_offset())) / sizeof(Klass*); |
1664 // Check for overflowing; use unsigned compare to handle the negative case. |
1664 // Check for overflowing; use unsigned compare to handle the negative case. |
1665 if( depth < ciKlass::primary_super_limit() ) { |
1665 if( depth < ciKlass::primary_super_limit() ) { |
1666 // The field is an element of Klass::_primary_supers. Return its (constant) value. |
1666 // The field is an element of Klass::_primary_supers. Return its (constant) value. |
1667 // (Folds up type checking code.) |
1667 // (Folds up type checking code.) |
1668 assert(Opcode() == Op_LoadKlass, "must load a klass from _primary_supers"); |
1668 assert(Opcode() == Op_LoadKlass, "must load a klass from _primary_supers"); |
1688 |
1688 |
1689 // We can still check if we are loading from the primary_supers array at a |
1689 // We can still check if we are loading from the primary_supers array at a |
1690 // shallow enough depth. Even though the klass is not exact, entries less |
1690 // shallow enough depth. Even though the klass is not exact, entries less |
1691 // than or equal to its super depth are correct. |
1691 // than or equal to its super depth are correct. |
1692 if (klass->is_loaded() ) { |
1692 if (klass->is_loaded() ) { |
1693 ciType *inner = klass->klass(); |
1693 ciType *inner = klass; |
1694 while( inner->is_obj_array_klass() ) |
1694 while( inner->is_obj_array_klass() ) |
1695 inner = inner->as_obj_array_klass()->base_element_type(); |
1695 inner = inner->as_obj_array_klass()->base_element_type(); |
1696 if( inner->is_instance_klass() && |
1696 if( inner->is_instance_klass() && |
1697 !inner->as_instance_klass()->flags().is_interface() ) { |
1697 !inner->as_instance_klass()->flags().is_interface() ) { |
1698 // Compute index into primary_supers array |
1698 // Compute index into primary_supers array |
1699 juint depth = (tkls->offset() - in_bytes(Klass::primary_supers_offset())) / sizeof(klassOop); |
1699 juint depth = (tkls->offset() - in_bytes(Klass::primary_supers_offset())) / sizeof(Klass*); |
1700 // Check for overflowing; use unsigned compare to handle the negative case. |
1700 // Check for overflowing; use unsigned compare to handle the negative case. |
1701 if( depth < ciKlass::primary_super_limit() && |
1701 if( depth < ciKlass::primary_super_limit() && |
1702 depth <= klass->super_depth() ) { // allow self-depth checks to handle self-check case |
1702 depth <= klass->super_depth() ) { // allow self-depth checks to handle self-check case |
1703 // The field is an element of Klass::_primary_supers. Return its (constant) value. |
1703 // The field is an element of Klass::_primary_supers. Return its (constant) value. |
1704 // (Folds up type checking code.) |
1704 // (Folds up type checking code.) |
1889 // Polymorphic factory method: |
1889 // Polymorphic factory method: |
1890 Node *LoadKlassNode::make( PhaseGVN& gvn, Node *mem, Node *adr, const TypePtr* at, const TypeKlassPtr *tk ) { |
1890 Node *LoadKlassNode::make( PhaseGVN& gvn, Node *mem, Node *adr, const TypePtr* at, const TypeKlassPtr *tk ) { |
1891 Compile* C = gvn.C; |
1891 Compile* C = gvn.C; |
1892 Node *ctl = NULL; |
1892 Node *ctl = NULL; |
1893 // sanity check the alias category against the created node type |
1893 // sanity check the alias category against the created node type |
1894 const TypeOopPtr *adr_type = adr->bottom_type()->isa_oopptr(); |
1894 const TypePtr *adr_type = adr->bottom_type()->isa_ptr(); |
1895 assert(adr_type != NULL, "expecting TypeOopPtr"); |
1895 assert(adr_type != NULL, "expecting TypeKlassPtr"); |
1896 #ifdef _LP64 |
1896 #ifdef _LP64 |
1897 if (adr_type->is_ptr_to_narrowoop()) { |
1897 if (adr_type->is_ptr_to_narrowoop()) { |
|
1898 assert(UseCompressedKlassPointers, "no compressed klasses"); |
1898 Node* load_klass = gvn.transform(new (C, 3) LoadNKlassNode(ctl, mem, adr, at, tk->make_narrowoop())); |
1899 Node* load_klass = gvn.transform(new (C, 3) LoadNKlassNode(ctl, mem, adr, at, tk->make_narrowoop())); |
1899 return new (C, 2) DecodeNNode(load_klass, load_klass->bottom_type()->make_ptr()); |
1900 return new (C, 2) DecodeNNode(load_klass, load_klass->bottom_type()->make_ptr()); |
1900 } |
1901 } |
1901 #endif |
1902 #endif |
1902 assert(!adr_type->is_ptr_to_narrowoop(), "should have got back a narrow oop"); |
1903 assert(!adr_type->is_ptr_to_narrowoop(), "should have got back a narrow oop"); |
2063 if (allocated_klass != NULL) { |
2064 if (allocated_klass != NULL) { |
2064 return allocated_klass; |
2065 return allocated_klass; |
2065 } |
2066 } |
2066 } |
2067 } |
2067 |
2068 |
2068 // Simplify k.java_mirror.as_klass to plain k, where k is a klassOop. |
2069 // Simplify k.java_mirror.as_klass to plain k, where k is a Klass*. |
2069 // Simplify ak.component_mirror.array_klass to plain ak, ak an arrayKlass. |
2070 // Simplify ak.component_mirror.array_klass to plain ak, ak an arrayKlass. |
2070 // See inline_native_Class_query for occurrences of these patterns. |
2071 // See inline_native_Class_query for occurrences of these patterns. |
2071 // Java Example: x.getClass().isAssignableFrom(y) |
2072 // Java Example: x.getClass().isAssignableFrom(y) |
2072 // Java Example: Array.newInstance(x.getClass().getComponentType(), n) |
2073 // Java Example: Array.newInstance(x.getClass().getComponentType(), n) |
2073 // |
2074 // |
2074 // This improves reflective code, often making the Class |
2075 // This improves reflective code, often making the Class |
2075 // mirror go completely dead. (Current exception: Class |
2076 // mirror go completely dead. (Current exception: Class |
2076 // mirrors may appear in debug info, but we could clean them out by |
2077 // mirrors may appear in debug info, but we could clean them out by |
2077 // introducing a new debug info operator for klassOop.java_mirror). |
2078 // introducing a new debug info operator for Klass*.java_mirror). |
2078 if (toop->isa_instptr() && toop->klass() == phase->C->env()->Class_klass() |
2079 if (toop->isa_instptr() && toop->klass() == phase->C->env()->Class_klass() |
2079 && (offset == java_lang_Class::klass_offset_in_bytes() || |
2080 && (offset == java_lang_Class::klass_offset_in_bytes() || |
2080 offset == java_lang_Class::array_klass_offset_in_bytes())) { |
2081 offset == java_lang_Class::array_klass_offset_in_bytes())) { |
2081 // We are loading a special hidden field from a Class mirror, |
2082 // We are loading a special hidden field from a Class mirror, |
2082 // the field which points to its Klass or arrayKlass metaobject. |
2083 // the field which points to its Klass or arrayKlass metaobject. |
2221 case T_CHAR: |
2222 case T_CHAR: |
2222 case T_SHORT: return new (C, 4) StoreCNode(ctl, mem, adr, adr_type, val); |
2223 case T_SHORT: return new (C, 4) StoreCNode(ctl, mem, adr, adr_type, val); |
2223 case T_LONG: return new (C, 4) StoreLNode(ctl, mem, adr, adr_type, val); |
2224 case T_LONG: return new (C, 4) StoreLNode(ctl, mem, adr, adr_type, val); |
2224 case T_FLOAT: return new (C, 4) StoreFNode(ctl, mem, adr, adr_type, val); |
2225 case T_FLOAT: return new (C, 4) StoreFNode(ctl, mem, adr, adr_type, val); |
2225 case T_DOUBLE: return new (C, 4) StoreDNode(ctl, mem, adr, adr_type, val); |
2226 case T_DOUBLE: return new (C, 4) StoreDNode(ctl, mem, adr, adr_type, val); |
|
2227 case T_METADATA: |
2226 case T_ADDRESS: |
2228 case T_ADDRESS: |
2227 case T_OBJECT: |
2229 case T_OBJECT: |
2228 #ifdef _LP64 |
2230 #ifdef _LP64 |
2229 if (adr->bottom_type()->is_ptr_to_narrowoop() || |
2231 if (adr->bottom_type()->is_ptr_to_narrowoop() || |
2230 (UseCompressedOops && val->bottom_type()->isa_klassptr() && |
2232 (UseCompressedKlassPointers && val->bottom_type()->isa_klassptr() && |
2231 adr->bottom_type()->isa_rawptr())) { |
2233 adr->bottom_type()->isa_rawptr())) { |
2232 val = gvn.transform(new (C, 2) EncodePNode(val, val->bottom_type()->make_narrowoop())); |
2234 val = gvn.transform(new (C, 2) EncodePNode(val, val->bottom_type()->make_narrowoop())); |
2233 return new (C, 4) StoreNNode(ctl, mem, adr, adr_type, val); |
2235 return new (C, 4) StoreNNode(ctl, mem, adr, adr_type, val); |
2234 } else |
2236 } else |
2235 #endif |
2237 #endif |