提交 2c3ef85f 编写于 作者: C coleenp

8004883: NPG: clean up anonymous class fix

Summary: Add klass_holder() to return either mirror or class_loader depending on if the class is anonymous or not.
Reviewed-by: stefank, jrose
上级 23a02b07
...@@ -496,21 +496,9 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const { ...@@ -496,21 +496,9 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const {
dest->verify_section_allocation(); dest->verify_section_allocation();
} }
// Anonymous classes need mirror to keep the metadata alive but // Append an oop reference that keeps the class alive.
// for regular classes, the class_loader is sufficient.
static void append_oop_references(GrowableArray<oop>* oops, Klass* k) { static void append_oop_references(GrowableArray<oop>* oops, Klass* k) {
if (k->oop_is_instance()) { oop cl = k->klass_holder();
InstanceKlass* ik = InstanceKlass::cast(k);
if (ik->is_anonymous()) {
oop o = ik->java_mirror();
assert (o != NULL, "should have a mirror");
if (!oops->contains(o)) {
oops->append(o);
}
return; // only need the mirror
}
}
oop cl = k->class_loader();
if (cl != NULL && !oops->contains(cl)) { if (cl != NULL && !oops->contains(cl)) {
oops->append(cl); oops->append(cl);
} }
......
...@@ -64,8 +64,10 @@ ...@@ -64,8 +64,10 @@
ClassLoaderData * ClassLoaderData::_the_null_class_loader_data = NULL; ClassLoaderData * ClassLoaderData::_the_null_class_loader_data = NULL;
ClassLoaderData::ClassLoaderData(Handle h_class_loader) : _class_loader(h_class_loader()), ClassLoaderData::ClassLoaderData(Handle h_class_loader, bool is_anonymous) :
_metaspace(NULL), _unloading(false), _keep_alive(false), _klasses(NULL), _class_loader(h_class_loader()),
_is_anonymous(is_anonymous), _keep_alive(is_anonymous), // initially
_metaspace(NULL), _unloading(false), _klasses(NULL),
_claimed(0), _jmethod_ids(NULL), _handles(NULL), _deallocate_list(NULL), _claimed(0), _jmethod_ids(NULL), _handles(NULL), _deallocate_list(NULL),
_next(NULL), _dependencies(NULL), _next(NULL), _dependencies(NULL),
_metaspace_lock(new Mutex(Monitor::leaf+1, "Metaspace allocation lock", true)) { _metaspace_lock(new Mutex(Monitor::leaf+1, "Metaspace allocation lock", true)) {
...@@ -257,13 +259,6 @@ void ClassLoaderData::remove_class(Klass* scratch_class) { ...@@ -257,13 +259,6 @@ void ClassLoaderData::remove_class(Klass* scratch_class) {
ShouldNotReachHere(); // should have found this class!! ShouldNotReachHere(); // should have found this class!!
} }
bool ClassLoaderData::is_anonymous() const {
Klass* k = _klasses;
return (_keep_alive || (k != NULL && k->oop_is_instance() &&
InstanceKlass::cast(k)->is_anonymous()));
}
void ClassLoaderData::unload() { void ClassLoaderData::unload() {
_unloading = true; _unloading = true;
...@@ -396,8 +391,7 @@ void ClassLoaderData::free_deallocate_list() { ...@@ -396,8 +391,7 @@ void ClassLoaderData::free_deallocate_list() {
// These anonymous class loaders are to contain classes used for JSR292 // These anonymous class loaders are to contain classes used for JSR292
ClassLoaderData* ClassLoaderData::anonymous_class_loader_data(oop loader, TRAPS) { ClassLoaderData* ClassLoaderData::anonymous_class_loader_data(oop loader, TRAPS) {
// Add a new class loader data to the graph. // Add a new class loader data to the graph.
ClassLoaderData* cld = ClassLoaderDataGraph::add(NULL, loader, CHECK_NULL); return ClassLoaderDataGraph::add(NULL, loader, CHECK_NULL);
return cld;
} }
const char* ClassLoaderData::loader_name() { const char* ClassLoaderData::loader_name() {
...@@ -475,7 +469,9 @@ ClassLoaderData* ClassLoaderDataGraph::add(ClassLoaderData** cld_addr, Handle lo ...@@ -475,7 +469,9 @@ ClassLoaderData* ClassLoaderDataGraph::add(ClassLoaderData** cld_addr, Handle lo
// Create one. // Create one.
ClassLoaderData* *list_head = &_head; ClassLoaderData* *list_head = &_head;
ClassLoaderData* next = _head; ClassLoaderData* next = _head;
ClassLoaderData* cld = new ClassLoaderData(loader);
bool is_anonymous = (cld_addr == NULL);
ClassLoaderData* cld = new ClassLoaderData(loader, is_anonymous);
if (cld_addr != NULL) { if (cld_addr != NULL) {
// First, Atomically set it // First, Atomically set it
...@@ -485,10 +481,6 @@ ClassLoaderData* ClassLoaderDataGraph::add(ClassLoaderData** cld_addr, Handle lo ...@@ -485,10 +481,6 @@ ClassLoaderData* ClassLoaderDataGraph::add(ClassLoaderData** cld_addr, Handle lo
// Returns the data. // Returns the data.
return old; return old;
} }
} else {
// Disallow unloading for this CLD during initialization if there is no
// class_loader oop to link this to.
cld->set_keep_alive(true);
} }
// We won the race, and therefore the task of adding the data to the list of // We won the race, and therefore the task of adding the data to the list of
......
...@@ -109,6 +109,7 @@ class ClassLoaderData : public CHeapObj<mtClass> { ...@@ -109,6 +109,7 @@ class ClassLoaderData : public CHeapObj<mtClass> {
Mutex* _metaspace_lock; // Locks the metaspace for allocations and setup. Mutex* _metaspace_lock; // Locks the metaspace for allocations and setup.
bool _unloading; // true if this class loader goes away bool _unloading; // true if this class loader goes away
bool _keep_alive; // if this CLD can be unloaded for anonymous loaders bool _keep_alive; // if this CLD can be unloaded for anonymous loaders
bool _is_anonymous; // if this CLD is for an anonymous class
volatile int _claimed; // true if claimed, for example during GC traces. volatile int _claimed; // true if claimed, for example during GC traces.
// To avoid applying oop closure more than once. // To avoid applying oop closure more than once.
// Has to be an int because we cas it. // Has to be an int because we cas it.
...@@ -139,7 +140,7 @@ class ClassLoaderData : public CHeapObj<mtClass> { ...@@ -139,7 +140,7 @@ class ClassLoaderData : public CHeapObj<mtClass> {
void set_next(ClassLoaderData* next) { _next = next; } void set_next(ClassLoaderData* next) { _next = next; }
ClassLoaderData* next() const { return _next; } ClassLoaderData* next() const { return _next; }
ClassLoaderData(Handle h_class_loader); ClassLoaderData(Handle h_class_loader, bool is_anonymous);
~ClassLoaderData(); ~ClassLoaderData();
void set_metaspace(Metaspace* m) { _metaspace = m; } void set_metaspace(Metaspace* m) { _metaspace = m; }
...@@ -174,12 +175,12 @@ class ClassLoaderData : public CHeapObj<mtClass> { ...@@ -174,12 +175,12 @@ class ClassLoaderData : public CHeapObj<mtClass> {
return _the_null_class_loader_data; return _the_null_class_loader_data;
} }
bool is_anonymous() const; bool is_anonymous() const { return _is_anonymous; }
static void init_null_class_loader_data() { static void init_null_class_loader_data() {
assert(_the_null_class_loader_data == NULL, "cannot initialize twice"); assert(_the_null_class_loader_data == NULL, "cannot initialize twice");
assert(ClassLoaderDataGraph::_head == NULL, "cannot initialize twice"); assert(ClassLoaderDataGraph::_head == NULL, "cannot initialize twice");
_the_null_class_loader_data = new ClassLoaderData((oop)NULL); _the_null_class_loader_data = new ClassLoaderData((oop)NULL, false);
ClassLoaderDataGraph::_head = _the_null_class_loader_data; ClassLoaderDataGraph::_head = _the_null_class_loader_data;
assert(_the_null_class_loader_data->is_the_null_class_loader_data(), "Must be"); assert(_the_null_class_loader_data->is_the_null_class_loader_data(), "Must be");
if (DumpSharedSpaces) { if (DumpSharedSpaces) {
......
...@@ -269,12 +269,10 @@ void CompileTask::initialize(int compile_id, ...@@ -269,12 +269,10 @@ void CompileTask::initialize(int compile_id,
const char* comment, const char* comment,
bool is_blocking) { bool is_blocking) {
assert(!_lock->is_locked(), "bad locking"); assert(!_lock->is_locked(), "bad locking");
InstanceKlass* holder = method->method_holder();
_compile_id = compile_id; _compile_id = compile_id;
_method = method(); _method = method();
_method_holder = JNIHandles::make_global( _method_holder = JNIHandles::make_global(method->method_holder()->klass_holder());
holder->is_anonymous() ? holder->java_mirror(): holder->class_loader());
_osr_bci = osr_bci; _osr_bci = osr_bci;
_is_blocking = is_blocking; _is_blocking = is_blocking;
_comp_level = comp_level; _comp_level = comp_level;
...@@ -298,10 +296,7 @@ void CompileTask::initialize(int compile_id, ...@@ -298,10 +296,7 @@ void CompileTask::initialize(int compile_id,
} else { } else {
_hot_method = hot_method(); _hot_method = hot_method();
// only add loader or mirror if different from _method_holder // only add loader or mirror if different from _method_holder
InstanceKlass* hot_holder = hot_method->method_holder(); _hot_method_holder = JNIHandles::make_global(hot_method->method_holder()->klass_holder());
_hot_method_holder = JNIHandles::make_global(
hot_holder->is_anonymous() ? hot_holder->java_mirror() :
hot_holder->class_loader());
} }
} }
} }
......
...@@ -538,6 +538,12 @@ class InstanceKlass: public Klass { ...@@ -538,6 +538,12 @@ class InstanceKlass: public Klass {
} }
} }
// Oop that keeps the metadata for this class from being unloaded
// in places where the metadata is stored in other places, like nmethods
oop klass_holder() const {
return is_anonymous() ? java_mirror() : class_loader();
}
// signers // signers
objArrayOop signers() const { return _signers; } objArrayOop signers() const { return _signers; }
void set_signers(objArrayOop s) { klass_oop_store((oop*)&_signers, s); } void set_signers(objArrayOop s) { klass_oop_store((oop*)&_signers, s); }
......
...@@ -451,6 +451,8 @@ class Klass : public Metadata { ...@@ -451,6 +451,8 @@ class Klass : public Metadata {
oop class_loader() const; oop class_loader() const;
virtual oop klass_holder() const { return class_loader(); }
protected: protected:
virtual Klass* array_klass_impl(bool or_null, int rank, TRAPS); virtual Klass* array_klass_impl(bool or_null, int rank, TRAPS);
virtual Klass* array_klass_impl(bool or_null, TRAPS); virtual Klass* array_klass_impl(bool or_null, TRAPS);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册