/* src/threads/threadlist.hpp - different thread-lists
- Copyright (C) 2008
+ Copyright (C) 1996-2011
CACAOVM - Verein zur Foerderung der freien virtuellen Maschine CACAO
This file is part of CACAO.
#include "toolbox/list.hpp"
+#include "vm/global.h"
+
/* ThreadList *****************************************************************/
#ifdef __cplusplus
-using std::list;
-
class ThreadList {
private:
static Mutex _mutex; // a mutex for all thread lists
- static list<threadobject*> _active_thread_list; // list of active threads
- static list<threadobject*> _free_thread_list; // list of free threads
- static list<int32_t> _free_index_list; // list of free thread indexes
+ static List<threadobject*> _active_thread_list; // list of active threads
+ static List<threadobject*> _free_thread_list; // list of free threads
+ static List<int32_t> _free_index_list; // list of free thread indexes
+ // Thread counters visible to Java.
+ static int32_t _number_of_started_java_threads;
+ static int32_t _number_of_active_java_threads;
+ static int32_t _peak_of_active_java_threads;
+
+ // Thread counters for internal usage.
static int32_t _number_of_non_daemon_threads;
- static inline void remove_from_active_thread_list(threadobject* t);
- static inline void add_to_free_thread_list(threadobject* t);
- static inline void add_to_free_index_list(int32_t index);
+ static int32_t _last_index;
+
+ static void remove_from_active_thread_list(threadobject* t);
+ static void add_to_free_thread_list(threadobject* t);
+ static void add_to_free_index_list(int32_t index);
private:
// Comparator class.
};
public:
- static inline void lock() { _mutex.lock(); }
- static inline void unlock() { _mutex.unlock(); }
+ static void lock() { _mutex.lock(); }
+ static void unlock() { _mutex.unlock(); }
+ static void wait_cond(Condition *cond) { cond->wait(_mutex); }
- // TODO make private
- static inline void add_to_active_thread_list(threadobject* t);
+ static void add_to_active_thread_list(threadobject* t);
- static void dump_threads();
- static inline threadobject* get_main_thread();
+ // Thread management methods.
+ static threadobject* get_main_thread();
static threadobject* get_free_thread();
static int32_t get_free_thread_index();
- static int32_t get_number_of_non_daemon_threads();
static threadobject* get_thread_by_index(int32_t index);
static threadobject* get_thread_from_java_object(java_handle_t* h);
- static void release_thread(threadobject* t);
+ static void release_thread(threadobject* t, bool needs_deactivate);
+ static void deactivate_thread(threadobject *t);
+
+ // Thread listing methods.
+ static void get_active_threads(List<threadobject*> &list);
+ static void get_active_java_threads(List<threadobject*> &list);
+
+ // Thread counting methods visible to Java.
+ static int32_t get_number_of_started_java_threads();
+ static int32_t get_number_of_active_java_threads();
+ static int32_t get_number_of_daemon_java_threads();
+ static int32_t get_peak_of_active_java_threads();
+ static void reset_peak_of_active_java_threads();
+
+ // Thread counting methods for internal use.
+ static int32_t get_number_of_active_threads();
+ static int32_t get_number_of_non_daemon_threads();
+
+ // Debugging methods.
+ static void dump_threads();
+};
+
+struct ThreadListLocker {
+ ThreadListLocker() { ThreadList::lock(); }
+ ~ThreadListLocker() { ThreadList::unlock(); }
};
inline void ThreadList::add_to_active_thread_list(threadobject* t)
{
+ lock();
_active_thread_list.push_back(t);
+ t->is_in_active_list = true;
+
+ // Update counter variables.
+ if ((t->flags & THREAD_FLAG_INTERNAL) == 0) {
+ _number_of_started_java_threads++;
+ _number_of_active_java_threads++;
+ _peak_of_active_java_threads = MAX(_peak_of_active_java_threads, _number_of_active_java_threads);
+ }
+ unlock();
}
inline void ThreadList::remove_from_active_thread_list(threadobject* t)
{
+ lock();
_active_thread_list.remove(t);
+ t->is_in_active_list = false;
+
+ // Update counter variables.
+ if ((t->flags & THREAD_FLAG_INTERNAL) == 0) {
+ _number_of_active_java_threads--;
+ }
+ unlock();
}
inline void ThreadList::add_to_free_thread_list(threadobject* t)
{
+ lock();
_free_thread_list.push_back(t);
+ unlock();
}
inline void ThreadList::add_to_free_index_list(int32_t index)
{
+ lock();
_free_index_list.push_back(index);
+ unlock();
}
inline threadobject* ThreadList::get_main_thread()
{
- return _active_thread_list.front();
+ lock();
+ threadobject *r = _active_thread_list.front();
+ unlock();
+ return r;
+}
+
+inline int32_t ThreadList::get_number_of_active_threads()
+{
+ lock();
+ int32_t size = _active_thread_list.size();
+ unlock();
+ return size;
+}
+
+inline int32_t ThreadList::get_number_of_started_java_threads()
+{
+ lock();
+ int32_t num = _number_of_started_java_threads;
+ unlock();
+ return num;
+}
+
+inline int32_t ThreadList::get_number_of_active_java_threads()
+{
+ lock();
+ int32_t num = _number_of_active_java_threads;
+ unlock();
+ return num;
+}
+
+inline int32_t ThreadList::get_peak_of_active_java_threads()
+{
+ lock();
+ int32_t num = _peak_of_active_java_threads;
+ unlock();
+ return num;
+}
+
+inline void ThreadList::reset_peak_of_active_java_threads()
+{
+ lock();
+ _peak_of_active_java_threads = _number_of_active_java_threads;
+ unlock();
}
#else
void ThreadList_lock();
void ThreadList_unlock();
void ThreadList_dump_threads();
-void ThreadList_release_thread(threadobject* t);
threadobject* ThreadList_get_free_thread();
int32_t ThreadList_get_free_thread_index();
void ThreadList_add_to_active_thread_list(threadobject* t);