Я изучаю, как сделать так, чтобы мой рабочий стол Linux оставался плавным и интерактивным, пока я выполняю задачи с интенсивным использованием ЦП в фоновом режиме. Вот пример программы (написанной на Java), которую я использую для имитации загрузки процессора:
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();
}
}
}
Когда я запускаю это в командной строке, я замечаю, что интерактивность моих настольных приложений (например, текстового редактора) значительно падает. У меня двухъядерный компьютер, поэтому меня это не удивляет.
Чтобы бороться с этим, моей первой мыслью было красиво процесс с renice -p 20 <pid>
. Однако я обнаружил, что это не сильно влияет. Вместо этого мне нужно перерисовать все дочерние процессы чем-то вроде ls /proc/<pid>/task | xargs renice 20 -p --
, что дает гораздо больший эффект.
Меня это очень смущает, поскольку я не ожидал, что потоки будут иметь собственные идентификаторы процесса. Даже если бы они это сделали, я бы ожидал, что renice
будет воздействовать на весь процесс, а не только на его основной поток.
Есть ли у кого-нибудь четкое представление о том, что здесь происходит? Похоже, что каждый поток на самом деле является отдельным процессом (по крайней мере, у него есть действующий PID). Я знал, что исторически Linux работал так, но я полагал, что NPTL исправил это много лет назад.
Я тестирую RHEL 5.4 (ядро Linux 2.6.18).
(Кстати. Я замечаю тот же эффект, если пытаюсь использовать sched_setscheduler(<pid>, SCHED_BATCH, ..)
, чтобы попытаться решить эту проблему интерактивности. То есть мне нужно сделать этот вызов для всех "дочерних" процессов, которые я вижу в /proc/<pid>/task
, этого недостаточно для выполнения это один раз в pid основной программы.)