comparison agent/src/share/classes/sun/jvm/hotspot/code/NMethod.java @ 6725:da91efe96a93

6964458: Reimplement class meta-data storage to use native memory Summary: Remove PermGen, allocate meta-data in metaspace linked to class loaders, rewrite GC walking, rewrite and rename metadata to be C++ classes Reviewed-by: jmasa, stefank, never, coleenp, kvn, brutisso, mgerdin, dholmes, jrose, twisti, roland Contributed-by: jmasa <jon.masamitsu@oracle.com>, stefank <stefan.karlsson@oracle.com>, mgerdin <mikael.gerdin@oracle.com>, never <tom.rodriguez@oracle.com>
author coleenp
date Sat, 01 Sep 2012 13:25:18 -0400
parents f6f3bb0ee072
children 5a98bf7d847b
comparison
equal deleted inserted replaced
6724:36d1d483d5d6 6725:da91efe96a93
1 /* 1 /*
2 * Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. 2 * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 * 4 *
5 * This code is free software; you can redistribute it and/or modify it 5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as 6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. 7 * published by the Free Software Foundation.
33 import sun.jvm.hotspot.types.*; 33 import sun.jvm.hotspot.types.*;
34 import sun.jvm.hotspot.utilities.*; 34 import sun.jvm.hotspot.utilities.*;
35 35
36 public class NMethod extends CodeBlob { 36 public class NMethod extends CodeBlob {
37 private static long pcDescSize; 37 private static long pcDescSize;
38 private static sun.jvm.hotspot.types.OopField methodField; 38 private static AddressField methodField;
39 /** != InvocationEntryBci if this nmethod is an on-stack replacement method */ 39 /** != InvocationEntryBci if this nmethod is an on-stack replacement method */
40 private static CIntegerField entryBCIField; 40 private static CIntegerField entryBCIField;
41 /** To support simple linked-list chaining of nmethods */ 41 /** To support simple linked-list chaining of nmethods */
42 private static AddressField osrLinkField; 42 private static AddressField osrLinkField;
43 private static AddressField scavengeRootLinkField; 43 private static AddressField scavengeRootLinkField;
48 private static CIntegerField deoptOffsetField; 48 private static CIntegerField deoptOffsetField;
49 private static CIntegerField deoptMhOffsetField; 49 private static CIntegerField deoptMhOffsetField;
50 private static CIntegerField origPCOffsetField; 50 private static CIntegerField origPCOffsetField;
51 private static CIntegerField stubOffsetField; 51 private static CIntegerField stubOffsetField;
52 private static CIntegerField oopsOffsetField; 52 private static CIntegerField oopsOffsetField;
53 private static CIntegerField metadataOffsetField;
53 private static CIntegerField scopesDataOffsetField; 54 private static CIntegerField scopesDataOffsetField;
54 private static CIntegerField scopesPCsOffsetField; 55 private static CIntegerField scopesPCsOffsetField;
55 private static CIntegerField dependenciesOffsetField; 56 private static CIntegerField dependenciesOffsetField;
56 private static CIntegerField handlerTableOffsetField; 57 private static CIntegerField handlerTableOffsetField;
57 private static CIntegerField nulChkTableOffsetField; 58 private static CIntegerField nulChkTableOffsetField;
86 } 87 }
87 88
88 private static void initialize(TypeDataBase db) { 89 private static void initialize(TypeDataBase db) {
89 Type type = db.lookupType("nmethod"); 90 Type type = db.lookupType("nmethod");
90 91
91 methodField = type.getOopField("_method"); 92 methodField = type.getAddressField("_method");
92 entryBCIField = type.getCIntegerField("_entry_bci"); 93 entryBCIField = type.getCIntegerField("_entry_bci");
93 osrLinkField = type.getAddressField("_osr_link"); 94 osrLinkField = type.getAddressField("_osr_link");
94 scavengeRootLinkField = type.getAddressField("_scavenge_root_link"); 95 scavengeRootLinkField = type.getAddressField("_scavenge_root_link");
95 scavengeRootStateField = type.getJByteField("_scavenge_root_state"); 96 scavengeRootStateField = type.getJByteField("_scavenge_root_state");
96 97
98 deoptOffsetField = type.getCIntegerField("_deoptimize_offset"); 99 deoptOffsetField = type.getCIntegerField("_deoptimize_offset");
99 deoptMhOffsetField = type.getCIntegerField("_deoptimize_mh_offset"); 100 deoptMhOffsetField = type.getCIntegerField("_deoptimize_mh_offset");
100 origPCOffsetField = type.getCIntegerField("_orig_pc_offset"); 101 origPCOffsetField = type.getCIntegerField("_orig_pc_offset");
101 stubOffsetField = type.getCIntegerField("_stub_offset"); 102 stubOffsetField = type.getCIntegerField("_stub_offset");
102 oopsOffsetField = type.getCIntegerField("_oops_offset"); 103 oopsOffsetField = type.getCIntegerField("_oops_offset");
104 metadataOffsetField = type.getCIntegerField("_metadata_offset");
103 scopesDataOffsetField = type.getCIntegerField("_scopes_data_offset"); 105 scopesDataOffsetField = type.getCIntegerField("_scopes_data_offset");
104 scopesPCsOffsetField = type.getCIntegerField("_scopes_pcs_offset"); 106 scopesPCsOffsetField = type.getCIntegerField("_scopes_pcs_offset");
105 dependenciesOffsetField = type.getCIntegerField("_dependencies_offset"); 107 dependenciesOffsetField = type.getCIntegerField("_dependencies_offset");
106 handlerTableOffsetField = type.getCIntegerField("_handler_table_offset"); 108 handlerTableOffsetField = type.getCIntegerField("_handler_table_offset");
107 nulChkTableOffsetField = type.getCIntegerField("_nul_chk_table_offset"); 109 nulChkTableOffsetField = type.getCIntegerField("_nul_chk_table_offset");
124 public Address getAddress() { 126 public Address getAddress() {
125 return addr; 127 return addr;
126 } 128 }
127 129
128 public Method getMethod() { 130 public Method getMethod() {
129 return (Method) VM.getVM().getObjectHeap().newOop(methodField.getValue(addr)); 131 return (Method)Metadata.instantiateWrapperFor(methodField.getValue(addr));
130 } 132 }
131 133
132 // Type info 134 // Type info
133 public boolean isNMethod() { return true; } 135 public boolean isNMethod() { return true; }
134 public boolean isJavaMethod() { return !getMethod().isNative(); } 136 public boolean isJavaMethod() { return !getMethod().isNative(); }
144 public Address deoptHandlerBegin() { return headerBegin().addOffsetTo(getDeoptOffset()); } 146 public Address deoptHandlerBegin() { return headerBegin().addOffsetTo(getDeoptOffset()); }
145 public Address deoptMhHandlerBegin() { return headerBegin().addOffsetTo(getDeoptMhOffset()); } 147 public Address deoptMhHandlerBegin() { return headerBegin().addOffsetTo(getDeoptMhOffset()); }
146 public Address stubBegin() { return headerBegin().addOffsetTo(getStubOffset()); } 148 public Address stubBegin() { return headerBegin().addOffsetTo(getStubOffset()); }
147 public Address stubEnd() { return headerBegin().addOffsetTo(getOopsOffset()); } 149 public Address stubEnd() { return headerBegin().addOffsetTo(getOopsOffset()); }
148 public Address oopsBegin() { return headerBegin().addOffsetTo(getOopsOffset()); } 150 public Address oopsBegin() { return headerBegin().addOffsetTo(getOopsOffset()); }
149 public Address oopsEnd() { return headerBegin().addOffsetTo(getScopesDataOffset()); } 151 public Address oopsEnd() { return headerBegin().addOffsetTo(getMetadataOffset()); }
152 public Address metadataBegin() { return headerBegin().addOffsetTo(getMetadataOffset()); }
153 public Address metadataEnd() { return headerBegin().addOffsetTo(getScopesDataOffset()); }
150 public Address scopesDataBegin() { return headerBegin().addOffsetTo(getScopesDataOffset()); } 154 public Address scopesDataBegin() { return headerBegin().addOffsetTo(getScopesDataOffset()); }
151 public Address scopesDataEnd() { return headerBegin().addOffsetTo(getScopesPCsOffset()); } 155 public Address scopesDataEnd() { return headerBegin().addOffsetTo(getScopesPCsOffset()); }
152 public Address scopesPCsBegin() { return headerBegin().addOffsetTo(getScopesPCsOffset()); } 156 public Address scopesPCsBegin() { return headerBegin().addOffsetTo(getScopesPCsOffset()); }
153 public Address scopesPCsEnd() { return headerBegin().addOffsetTo(getDependenciesOffset()); } 157 public Address scopesPCsEnd() { return headerBegin().addOffsetTo(getDependenciesOffset()); }
154 public Address dependenciesBegin() { return headerBegin().addOffsetTo(getDependenciesOffset()); } 158 public Address dependenciesBegin() { return headerBegin().addOffsetTo(getDependenciesOffset()); }
160 164
161 public int constantsSize() { return (int) constantsEnd() .minus(constantsBegin()); } 165 public int constantsSize() { return (int) constantsEnd() .minus(constantsBegin()); }
162 public int instsSize() { return (int) instsEnd() .minus(instsBegin()); } 166 public int instsSize() { return (int) instsEnd() .minus(instsBegin()); }
163 public int stubSize() { return (int) stubEnd() .minus(stubBegin()); } 167 public int stubSize() { return (int) stubEnd() .minus(stubBegin()); }
164 public int oopsSize() { return (int) oopsEnd() .minus(oopsBegin()); } 168 public int oopsSize() { return (int) oopsEnd() .minus(oopsBegin()); }
169 public int metadataSize() { return (int) metadataEnd() .minus(metadataBegin()); }
165 public int scopesDataSize() { return (int) scopesDataEnd() .minus(scopesDataBegin()); } 170 public int scopesDataSize() { return (int) scopesDataEnd() .minus(scopesDataBegin()); }
166 public int scopesPCsSize() { return (int) scopesPCsEnd() .minus(scopesPCsBegin()); } 171 public int scopesPCsSize() { return (int) scopesPCsEnd() .minus(scopesPCsBegin()); }
167 public int dependenciesSize() { return (int) dependenciesEnd().minus(dependenciesBegin()); } 172 public int dependenciesSize() { return (int) dependenciesEnd().minus(dependenciesBegin()); }
168 public int handlerTableSize() { return (int) handlerTableEnd().minus(handlerTableBegin()); } 173 public int handlerTableSize() { return (int) handlerTableEnd().minus(handlerTableBegin()); }
169 public int nulChkTableSize() { return (int) nulChkTableEnd() .minus(nulChkTableBegin()); } 174 public int nulChkTableSize() { return (int) nulChkTableEnd() .minus(nulChkTableBegin()); }
183 188
184 public boolean constantsContains (Address addr) { return constantsBegin() .lessThanOrEqual(addr) && constantsEnd() .greaterThan(addr); } 189 public boolean constantsContains (Address addr) { return constantsBegin() .lessThanOrEqual(addr) && constantsEnd() .greaterThan(addr); }
185 public boolean instsContains (Address addr) { return instsBegin() .lessThanOrEqual(addr) && instsEnd() .greaterThan(addr); } 190 public boolean instsContains (Address addr) { return instsBegin() .lessThanOrEqual(addr) && instsEnd() .greaterThan(addr); }
186 public boolean stubContains (Address addr) { return stubBegin() .lessThanOrEqual(addr) && stubEnd() .greaterThan(addr); } 191 public boolean stubContains (Address addr) { return stubBegin() .lessThanOrEqual(addr) && stubEnd() .greaterThan(addr); }
187 public boolean oopsContains (Address addr) { return oopsBegin() .lessThanOrEqual(addr) && oopsEnd() .greaterThan(addr); } 192 public boolean oopsContains (Address addr) { return oopsBegin() .lessThanOrEqual(addr) && oopsEnd() .greaterThan(addr); }
193 public boolean metadataContains (Address addr) { return metadataBegin() .lessThanOrEqual(addr) && metadataEnd() .greaterThan(addr); }
188 public boolean scopesDataContains (Address addr) { return scopesDataBegin() .lessThanOrEqual(addr) && scopesDataEnd() .greaterThan(addr); } 194 public boolean scopesDataContains (Address addr) { return scopesDataBegin() .lessThanOrEqual(addr) && scopesDataEnd() .greaterThan(addr); }
189 public boolean scopesPCsContains (Address addr) { return scopesPCsBegin() .lessThanOrEqual(addr) && scopesPCsEnd() .greaterThan(addr); } 195 public boolean scopesPCsContains (Address addr) { return scopesPCsBegin() .lessThanOrEqual(addr) && scopesPCsEnd() .greaterThan(addr); }
190 public boolean handlerTableContains(Address addr) { return handlerTableBegin().lessThanOrEqual(addr) && handlerTableEnd().greaterThan(addr); } 196 public boolean handlerTableContains(Address addr) { return handlerTableBegin().lessThanOrEqual(addr) && handlerTableEnd().greaterThan(addr); }
191 public boolean nulChkTableContains (Address addr) { return nulChkTableBegin() .lessThanOrEqual(addr) && nulChkTableEnd() .greaterThan(addr); } 197 public boolean nulChkTableContains (Address addr) { return nulChkTableBegin() .lessThanOrEqual(addr) && nulChkTableEnd() .greaterThan(addr); }
192 198
193 public int getOopsLength() { return (int) (oopsSize() / VM.getVM().getOopSize()); } 199 public int getOopsLength() { return (int) (oopsSize() / VM.getVM().getOopSize()); }
200 public int getMetadataLength() { return (int) (metadataSize() / VM.getVM().getOopSize()); }
194 201
195 /** Entry points */ 202 /** Entry points */
196 public Address getEntryPoint() { return entryPointField.getValue(addr); } 203 public Address getEntryPoint() { return entryPointField.getValue(addr); }
197 public Address getVerifiedEntryPoint() { return verifiedEntryPointField.getValue(addr); } 204 public Address getVerifiedEntryPoint() { return verifiedEntryPointField.getValue(addr); }
198 205
201 if (index == 0) return null; 208 if (index == 0) return null;
202 if (Assert.ASSERTS_ENABLED) { 209 if (Assert.ASSERTS_ENABLED) {
203 Assert.that(index > 0 && index <= getOopsLength(), "must be a valid non-zero index"); 210 Assert.that(index > 0 && index <= getOopsLength(), "must be a valid non-zero index");
204 } 211 }
205 return oopsBegin().getOopHandleAt((index - 1) * VM.getVM().getOopSize()); 212 return oopsBegin().getOopHandleAt((index - 1) * VM.getVM().getOopSize());
213 }
214
215 /** Support for metadata in scopes and relocs. Note: index 0 is reserved for null. */
216 public Address getMetadataAt(int index) {
217 if (index == 0) return null;
218 if (Assert.ASSERTS_ENABLED) {
219 Assert.that(index > 0 && index <= getMetadataLength(), "must be a valid non-zero index");
220 }
221 return metadataBegin().getAddressAt((index - 1) * VM.getVM().getOopSize());
222 }
223
224 public Method getMethodAt(int index) {
225 return (Method)Metadata.instantiateWrapperFor(getMetadataAt(index));
206 } 226 }
207 227
208 // FIXME: add interpreter_entry_point() 228 // FIXME: add interpreter_entry_point()
209 // FIXME: add lazy_interpreter_entry_point() for C2 229 // FIXME: add lazy_interpreter_entry_point() for C2
210 230
410 private int getExceptionOffset() { return (int) exceptionOffsetField .getValue(addr); } 430 private int getExceptionOffset() { return (int) exceptionOffsetField .getValue(addr); }
411 private int getDeoptOffset() { return (int) deoptOffsetField .getValue(addr); } 431 private int getDeoptOffset() { return (int) deoptOffsetField .getValue(addr); }
412 private int getDeoptMhOffset() { return (int) deoptMhOffsetField .getValue(addr); } 432 private int getDeoptMhOffset() { return (int) deoptMhOffsetField .getValue(addr); }
413 private int getStubOffset() { return (int) stubOffsetField .getValue(addr); } 433 private int getStubOffset() { return (int) stubOffsetField .getValue(addr); }
414 private int getOopsOffset() { return (int) oopsOffsetField .getValue(addr); } 434 private int getOopsOffset() { return (int) oopsOffsetField .getValue(addr); }
435 private int getMetadataOffset() { return (int) metadataOffsetField .getValue(addr); }
415 private int getScopesDataOffset() { return (int) scopesDataOffsetField .getValue(addr); } 436 private int getScopesDataOffset() { return (int) scopesDataOffsetField .getValue(addr); }
416 private int getScopesPCsOffset() { return (int) scopesPCsOffsetField .getValue(addr); } 437 private int getScopesPCsOffset() { return (int) scopesPCsOffsetField .getValue(addr); }
417 private int getDependenciesOffset() { return (int) dependenciesOffsetField.getValue(addr); } 438 private int getDependenciesOffset() { return (int) dependenciesOffsetField.getValue(addr); }
418 private int getHandlerTableOffset() { return (int) handlerTableOffsetField.getValue(addr); } 439 private int getHandlerTableOffset() { return (int) handlerTableOffsetField.getValue(addr); }
419 private int getNulChkTableOffset() { return (int) nulChkTableOffsetField .getValue(addr); } 440 private int getNulChkTableOffset() { return (int) nulChkTableOffsetField .getValue(addr); }