*/
static pthread_t GC_thread;
static char *CtdlThreadStates[CTDL_THREAD_LAST_STATE];
-double CtdlThreadLoadAvg;
-
+double CtdlThreadLoadAvg = 0;
+double CtdlThreadWorkerAvg = 0;
/*
* Pinched the following bits regarding signals from Kannel.org
*/
// CtdlThreadGC();
}
+/*
+ * A quick function to show the load averages
+ */
+void ctdl_thread_internal_calc_loadavg(void)
+{
+ struct CtdlThreadNode *that_thread;
+ double load_avg, worker_avg;
+ int workers = 0;
+ begin_critical_section(S_THREAD_LIST);
+ that_thread = CtdlThreadList;
+ load_avg = 0;
+ worker_avg = 0;
+ while(that_thread)
+ {
+ /* Update load averages */
+ ctdl_thread_internal_update_avgs(that_thread);
+ pthread_mutex_lock(&that_thread->ThreadMutex);
+ that_thread->load_avg = that_thread->avg_sleeping + that_thread->avg_running + that_thread->avg_blocked;
+ that_thread->load_avg = that_thread->avg_running / that_thread->load_avg / 100;
+ that_thread->avg_sleeping /= 2;
+ that_thread->avg_running /= 2;
+ that_thread->avg_blocked /= 2;
+ load_avg += that_thread->load_avg;
+ if (that_thread->flags & CTDLTHREAD_WORKER)
+ {
+ worker_avg += that_thread->load_avg;
+ workers++;
+ }
+/* CtdlLogPrintf(CTDL_DEBUG, "CtdlThread, \"%s\" (%ld) \"%s\" %f %f %f %f.\n",
+ that_thread->name,
+ that_thread->tid,
+ CtdlThreadStates[that_thread->state],
+ that_thread->avg_sleeping,
+ that_thread->avg_running,
+ that_thread->avg_blocked,
+ that_thread->load_avg);
+*/
+ pthread_mutex_unlock(&that_thread->ThreadMutex);
+ that_thread = that_thread->next;
+ }
+ CtdlThreadLoadAvg = load_avg/num_threads;
+ CtdlThreadWorkerAvg = worker_avg/workers;
+// CtdlLogPrintf(CTDL_INFO, "System load average %f, workers averag %f\n", CtdlThreadLoadAvg, CtdlThreadWorkerAvg);
+ end_critical_section(S_THREAD_LIST);
+}
/*
*/
void ctdl_internal_thread_gc (void)
{
- struct CtdlThreadNode *this_thread, *that_thread = NULL;
- double load_avg;
+ struct CtdlThreadNode *this_thread, *that_thread;
int workers = 0;
- /*
- * Wait on the condition variable that tells us garbage collection is needed
- * We wake up every 10 seconds just in case someone forgot to inform us of a thread exiting
- */
-
- CtdlThreadSleep(10);
-
/* Handle exiting of garbage collector thread */
if(num_threads == 1)
CtdlThreadList->state = CTDL_THREAD_EXITED;
*/
begin_critical_section(S_THREAD_LIST);
this_thread = CtdlThreadList;
- load_avg = 0;
while(this_thread)
{
that_thread = this_thread;
this_thread = this_thread->next;
- /* Update load averages */
- ctdl_thread_internal_update_avgs(that_thread);
- pthread_mutex_lock(&that_thread->ThreadMutex);
- that_thread->load_avg = that_thread->avg_sleeping + that_thread->avg_running + that_thread->avg_blocked;
- that_thread->load_avg = that_thread->avg_running / that_thread->load_avg / 100;
- that_thread->avg_sleeping /= 10;
- that_thread->avg_running /= 10;
- that_thread->avg_blocked /= 10;
- load_avg += that_thread->load_avg;
-
- CtdlLogPrintf(CTDL_DEBUG, "CtdlThread, \"%s\" (%ld) \"%s\" %f %f %f %f.\n", that_thread->name, that_thread->tid, CtdlThreadStates[that_thread->state], that_thread->avg_sleeping, that_thread->avg_running, that_thread->avg_blocked, that_thread->load_avg);
- pthread_mutex_unlock(&that_thread->ThreadMutex);
-
/* Do we need to clean up this thread? */
if (that_thread->state != CTDL_THREAD_EXITED)
{
CtdlLogPrintf(CTDL_EMERG, "Thread system PANIC, discrepancy in number of worker threads. Counted %d, should be %d.\n", workers, num_workers);
return;
}
- CtdlThreadLoadAvg = load_avg/num_threads;
end_critical_section(S_THREAD_LIST);
- CtdlLogPrintf(CTDL_INFO, "System load average %f.\n", CtdlThreadLoadAvg);
}