134
135 // Integer for 0 and 1 are in java/lang/Integer$IntegerCache and are archived
136 ADD_EXCL("sun/invoke/util/ValueConversions", "ONE_INT", // E
137 "ZERO_INT"); // E
138
139 if (CDSConfig::is_dumping_method_handles()) {
140 ADD_EXCL("java/lang/invoke/InvokerBytecodeGenerator", "MEMBERNAME_FACTORY", // D
141 "CD_Object_array", // E same as <...>ConstantUtils.CD_Object_array::CD_Object
142 "INVOKER_SUPER_DESC"); // E same as java.lang.constant.ConstantDescs::CD_Object
143
144 ADD_EXCL("java/lang/runtime/ObjectMethods", "CLASS_IS_INSTANCE", // D
145 "FALSE", // D
146 "TRUE", // D
147 "ZERO"); // D
148 }
149
150 if (CDSConfig::is_dumping_aot_linked_classes()) {
151 ADD_EXCL("java/lang/Package$VersionInfo", "NULL_VERSION_INFO"); // D
152 }
153
154 # undef ADD_EXCL
155
156 ClassLoaderDataGraph::classes_do(this);
157 }
158
159 CDSHeapVerifier::~CDSHeapVerifier() {
160 if (_problems > 0) {
161 log_error(aot, heap)("Scanned %d objects. Found %d case(s) where "
162 "an object points to a static field that "
163 "may hold a different value at runtime.", _archived_objs, _problems);
164 log_error(aot, heap)("Please see cdsHeapVerifier.cpp and aotClassInitializer.cpp for details");
165 AOTMetaspace::unrecoverable_writing_error();
166 }
167 }
168
169 class CDSHeapVerifier::CheckStaticFields : public FieldClosure {
170 CDSHeapVerifier* _verifier;
171 InstanceKlass* _ik; // The class whose static fields are being checked.
172 const char** _exclusions;
173 public:
174 CheckStaticFields(CDSHeapVerifier* verifier, InstanceKlass* ik)
175 : _verifier(verifier), _ik(ik) {
176 _exclusions = _verifier->find_exclusion(_ik);
177 }
178
179 void do_field(fieldDescriptor* fd) {
180 if (fd->field_type() != T_OBJECT) {
181 return;
182 }
183
184 if (fd->signature()->equals("Ljdk/internal/access/JavaLangAccess;")) {
185 // A few classes have static fields that point to SharedSecrets.getJavaLangAccess().
186 // This object carries no state and we can create a new one in the production run.
187 return;
188 }
189 oop static_obj_field = _ik->java_mirror()->obj_field(fd->offset());
190 if (static_obj_field != nullptr) {
191 Klass* field_type = static_obj_field->klass();
192 if (_exclusions != nullptr) {
193 for (const char** p = _exclusions; *p != nullptr; p++) {
194 if (fd->name()->equals(*p)) {
195 return;
196 }
197 }
198 }
199
200 if (fd->is_final() && java_lang_String::is_instance(static_obj_field) && fd->has_initial_value()) {
201 // This field looks like like this in the Java source:
202 // static final SOME_STRING = "a string literal";
203 // This string literal has been stored in the shared string table, so it's OK
204 // for the archived objects to refer to it.
205 return;
206 }
207 if (fd->is_final() && java_lang_Class::is_instance(static_obj_field)) {
208 // This field points to an archived mirror.
|
134
135 // Integer for 0 and 1 are in java/lang/Integer$IntegerCache and are archived
136 ADD_EXCL("sun/invoke/util/ValueConversions", "ONE_INT", // E
137 "ZERO_INT"); // E
138
139 if (CDSConfig::is_dumping_method_handles()) {
140 ADD_EXCL("java/lang/invoke/InvokerBytecodeGenerator", "MEMBERNAME_FACTORY", // D
141 "CD_Object_array", // E same as <...>ConstantUtils.CD_Object_array::CD_Object
142 "INVOKER_SUPER_DESC"); // E same as java.lang.constant.ConstantDescs::CD_Object
143
144 ADD_EXCL("java/lang/runtime/ObjectMethods", "CLASS_IS_INSTANCE", // D
145 "FALSE", // D
146 "TRUE", // D
147 "ZERO"); // D
148 }
149
150 if (CDSConfig::is_dumping_aot_linked_classes()) {
151 ADD_EXCL("java/lang/Package$VersionInfo", "NULL_VERSION_INFO"); // D
152 }
153
154 if (CDSConfig::is_dumping_dynamic_proxies()) {
155 ADD_EXCL("java/lang/reflect/ProxyGenerator", "CD_Object_array"); // D
156 }
157
158 // These are used by BuiltinClassLoader::negativeLookupCache, etc but seem to be
159 // OK. TODO - we should completely disable the caching unless ArchiveLoaderLookupCache
160 // is enabled
161 ADD_EXCL("java/lang/Boolean", "TRUE", // E
162 "FALSE"); // E
163
164 # undef ADD_EXCL
165
166 ClassLoaderDataGraph::classes_do(this);
167 }
168
169 CDSHeapVerifier::~CDSHeapVerifier() {
170 if (_problems > 0) {
171 log_error(aot, heap)("Scanned %d objects. Found %d case(s) where "
172 "an object points to a static field that "
173 "may hold a different value at runtime.", _archived_objs, _problems);
174 log_error(aot, heap)("Please see cdsHeapVerifier.cpp and aotClassInitializer.cpp for details");
175 AOTMetaspace::unrecoverable_writing_error();
176 }
177 }
178
179 class CDSHeapVerifier::CheckStaticFields : public FieldClosure {
180 CDSHeapVerifier* _verifier;
181 InstanceKlass* _ik; // The class whose static fields are being checked.
182 const char** _exclusions;
183 public:
184 CheckStaticFields(CDSHeapVerifier* verifier, InstanceKlass* ik)
185 : _verifier(verifier), _ik(ik) {
186 _exclusions = _verifier->find_exclusion(_ik);
187 }
188
189 void do_field(fieldDescriptor* fd) {
190 if (fd->field_type() != T_OBJECT) {
191 return;
192 }
193
194 if (fd->signature()->equals("Ljdk/internal/access/JavaLangAccess;") ||
195 fd->signature()->equals("Ljdk/internal/access/JavaLangReflectAccess;")) {
196 // A few classes have static fields that point to SharedSecrets.get???Access().
197 // This object carries no state and we can create a new one in the production run.
198 return;
199 }
200 if (fd->signature()->equals("Ljdk/internal/reflect/ReflectionFactory;")) {
201 return;
202 }
203 oop static_obj_field = _ik->java_mirror()->obj_field(fd->offset());
204 if (static_obj_field != nullptr) {
205 Klass* field_type = static_obj_field->klass();
206 if (_exclusions != nullptr) {
207 for (const char** p = _exclusions; *p != nullptr; p++) {
208 if (fd->name()->equals(*p)) {
209 return;
210 }
211 }
212 }
213
214 if (fd->is_final() && java_lang_String::is_instance(static_obj_field) && fd->has_initial_value()) {
215 // This field looks like like this in the Java source:
216 // static final SOME_STRING = "a string literal";
217 // This string literal has been stored in the shared string table, so it's OK
218 // for the archived objects to refer to it.
219 return;
220 }
221 if (fd->is_final() && java_lang_Class::is_instance(static_obj_field)) {
222 // This field points to an archived mirror.
|