I am investigating how to have my Linux desktop experience remain smooth and interactive while I run CPU intensive tasks in the background. Here is the sample program (written in Java) which I am using to simulate CPU load:
public class Spinner {
public static void main(String[] args)
{
for (int i = 0; i < 100; i++) {
(new Thread(new Runnable() {
public void run() {
while (true);
}
})).start();
}
}
}
When I run this on the command line, I notice that the interactivity of my desktop applicaitons (e.g. text editor) drops significantly. I have a dual core machine, so I am not suprised by this.
To combat this my first thought was to nice the process with renice -p 20 <pid>
. I found however that this doesn't have much affect. I instead have to renice all of the child processes with something like ls /proc/<pid>/task | xargs renice 20 -p --
which has a much greater effect.
I am very confused by this, as I would not expect threads to have their own process IDs. Even if they did I would expect renice
to act on the entire process, not just the main thread of the process.
Does anyone have a clear understanding of what is happening here? It appears that each thread is actually a seperate process (at least it has a valid PID). I knew that historically Linux worked like this, but I believed NPTL fixed that years ago.
I am testing on RHEL 5.4 (linux kernel 2.6.18).
(As an aside. I notice the same effect if I try to use sched_setscheduler(<pid>, SCHED_BATCH, ..)
to try to solve this interactivity problem. Ie, I need to make this call for all the "child" processes I seee in /proc/<pid>/task
, it is not enough to perform it once on the main program pid.)