bool check_seen_thread(Thread* thread, PlaceholderTable::classloadAction action) { assert_lock_strong(SystemDictionary_lock); SeenThread* threadQ = actionToQueue(action); SeenThread* seen = threadQ; while (seen) { if (thread == seen->thread()) { return true; } seen = seen->next(); } return false; }
// returns true if seenthreadQ is now empty // Note, caller must ensure probe still exists while holding // SystemDictionary_lock // ignores if cleanup has already been done // if found, deletes SeenThread bool remove_seen_thread(Thread* thread, PlaceholderTable::classloadAction action) { assert_lock_strong(SystemDictionary_lock); SeenThread* threadQ = actionToQueue(action); SeenThread* seen = threadQ; SeenThread* prev = NULL; while (seen) { if (thread == seen->thread()) { if (prev) { prev->set_next(seen->next()); } else { set_threadQ(seen->next(), action); } if (seen->next()) { seen->next()->set_prev(prev); } delete seen; break; } prev = seen; seen = seen->next(); } return (actionToQueue(action) == NULL); }
// Doubly-linked list of Threads per action for class/classloader pair // Class circularity support: links in thread before loading superclass // bootstrapsearchpath support: links in a thread before load_instance_class // definers: use as queue of define requestors, including owner of // define token. Appends for debugging of requestor order void add_seen_thread(Thread* thread, PlaceholderTable::classloadAction action) { assert_lock_strong(SystemDictionary_lock); SeenThread* threadEntry = new SeenThread(thread); SeenThread* seen = actionToQueue(action); if (seen == NULL) { set_threadQ(threadEntry, action); return; } SeenThread* next; while ((next = seen->next()) != NULL) { seen = next; } seen->set_next(threadEntry); threadEntry->set_prev(seen); return; }