Можно ли временно заморозить процесс в Linux?

Мне было интересно, есть ли способ заморозить любой процесс в течение определенного времени?

Я имею в виду следующее: возможно ли, чтобы одно приложение (возможно, выполнялось как root) приостановило выполнение другого уже запущенного процесса (любой процесс, как графический интерфейс, так и командную строку), а затем возобновить его позже? Другими словами, я не хочу, чтобы определенные процессы планировались планировщиком linux в течение определенного времени.

См. Здесь

Существует два сигнала, которые могут приостановить выполнение процесса. Один из них «изящный», а один «силен».

«Изящный» – это SIGTSTP , и его цель – «красиво» попросить процесс, если он захочет, приостановить выполнение, пока не получит SIGCONT . В случае SIGTSTP процесс может игнорировать SIGTSTP и продолжать выполнение в любом случае, поэтому для этого требуется сотрудничество с программой, предназначенной для обработки SIGTSTP.

«Сильным» является SIGSTOP , и его цель – приостановить все потоки пользовательского пространства, связанные с этим процессом. Для процесса так же невозможно игнорировать SIGSTOP поскольку он должен игнорировать SIGKILL (последний сильно убивает процесс).

Чтобы отправить произвольный сигнал, включая любой из упомянутых здесь, вы можете использовать такие программы, как kill , killall или pkill ; Или используйте системный вызов kill(2) . Ознакомьтесь с файлами вашей операционной системы для информации о платформе / архитектуре / версии и ошибках, относящихся к любому из вышеперечисленных. Обратите внимание, что слово «kill» во всех этих командах и syscall – плохое неправильное имя. Эти команды не предназначены исключительно для прекращения процессов. Они могут это сделать, отправив некоторые сигналы; Но сигналы могут также использоваться для функциональности, отличной от завершения процесса. Например, SIGSTOP только приостанавливает процесс, и это всего лишь один из нескольких сигналов, которые можно отправить таким образом.

Чтобы добавить условие автоматического возобновления процесса по прошествии определенного периода времени, вам нужно будет использовать какой-то процесс мониторинга, который остается запущенным, и устанавливает таймер для пробуждения процесса мониторинга, который затем вызывает kill(2) и отправляет сигнал SIGCONT на остановленный процесс, чтобы запросить ядро ​​возобновить выполнение. Обратите внимание, что Linux имеет несколько механизмов синхронизации с различной степенью точности и точности; Кроме того, если ваша система очень занята, ваш процесс мониторинга может не проснуться до тех пор, пока не истечет его таймер, и, следовательно, пробуждение может быть отложено.

Если вы полагаетесь на очень точную точность приостановки и возобновления приостановленного процесса, вам может потребоваться запустить вашу программу мониторинга с разрешениями в реальном времени (см. Эту справочную страницу в sched_setscheduler(2) для получения информации о создании вашего процесса в режиме реального времени). Вы также можете использовать High-Resolution Timers, функцию ядра Linux (которая доступна только в том случае, если ваше оборудование поддерживает их), в сочетании с планированием в реальном времени, чтобы получить очень точную, субмиллисекундную точность по времени, затем Пробуждение и отправить сигнал, чтобы возобновить контролируемый процесс очень быстро.

Вы не указали, какие технологии вы готовы использовать для реализации этого. На минимальном уровне вам понадобится хотя бы bash-скриптинг, хотя вы не сможете получить очень мелкие сроки. Вот сценарий bash (непроверенный, так что будьте осторожны), что является просто доказательством концепции вашего запроса. Если вам нужна точная синхронизация, вам придется написать программу, возможно, на C / C ++ или на другом родном языке, а также использовать планирование в реальном времени и hrtimers.

 #!/bin/bash #This is the process you want to suspend. screen -mdS child bash -c "cat /dev/urandom | base64" #This is the process ID of the child process THEPID=$(screen -list | grep child | cut -f1 -d'.' | sed 's/\W//g') #Send SIGSTOP to the child process. kill -SIGSTOP ${THEPID} #Now it is suspended. This process will sleep for 10 seconds asynchronously, then resume the process. screen -mdS monitor bash -c "sleep 10; kill -SIGCONT ${THEPID}" 

Обратите внимание, что сценарий закончится, и скрипт управления завершится, но из-за screen контролирующего процесс монитора, он будет продолжать работать в фоновом режиме в течение 10 секунд (на основе аргумента, переданного в sleep ), а затем просыпаться и продолжать дочерний процесс , Но это будет долго после завершения контрольного сценария. Если вы хотите синхронно ждать, пока время истечет, просто опустите второй вызов на screen и выполните жесткий код сна и убейте в управляющий скрипт.

Вы можете проверить, что процесс фактически приостанавливается запуском

screen -rS child

После запуска этого скрипта. Вы ничего не увидите на консоли. Затем, по истечении таймера (10 секунд), он наводнит ваш экран данными base64 (случайные символы от 0 до 9 и AF). Нажмите Ctrl + C, чтобы выйти.

Если у вас есть неплохое определение «замораживание», вы можете проверить команду renice .

Renice позволяет изменять приоритет планирования запущенных процессов.

Нормальное значение nice процесса равно 0. Увеличение приятного значения делает процесс более приятным, например, «почему бы вам не пойти первым». Уменьшение приятного значения делает процесс менее приятным, так как «сойди с пути, я спешу». Хороший диапазон значений – от -20 до 19.

Любой может сделать свои собственные процессы более приятными. Только root может сделать процесс менее приятным или изменить приятность других пользователей.

Если вы установите значение nice процессов равным 19, оно будет работать только тогда, когда ничего не хочет в системе.

Вот пример, который запускается в локальном ящике Linux.

Используйте ps -l и посмотрите на столбец NI, чтобы увидеть, что процессы имеют хорошее значение.

 -> ps -l
 FS UID PID PPID C PRI NI ADDR SZ WCHAN TTY CMD
 0 S 29190 402 31146 0 75 0 - 16547 wait pts / 0 bash
 0 T 29190 1105 402 0 75 0 - 23980 финиш pts / 0 vim
 0 R 29190 794 402 0 76 0 - 15874 - pts / 0 ps

Запуск renice +10 в процессе vim заставляет его работать с меньшим приоритетом.

 -> renice +10 -p 1105
 1105: старый приоритет 0, новый приоритет 10

 -> ps -l
 FS UID PID PPID C PRI NI ADDR SZ WCHAN TTY CMD
 0 S 29190 402 31146 0 76 0 - 16547 wait pts / 0 bash
 0 T 29190 1105 402 0 95 10 - 23980 финиш pts / 0 vim
 0 R 29190 1998 402 0 78 0 - 15874 - pts / 0 ps

Предполагая, что вы можете растянуть «заморозить», чтобы означать «не беспокоить кого-либо еще в системе», вы можете записать что-то вроде:

 Renice 20 -p & ltpid интереса>
 Сон & lt; количество времени>
 Renice 0 -p & ltpid интереса>

(Не забудьте запустить его как root).


Обратите внимание, что я взял некоторые свободы с вышеприведенным выходом ps -l чтобы получить интересные столбцы, чтобы они хорошо отображались в маленьких синих ящиках 🙂

Да, вы можете это сделать, отправив сигнал STOP на процесс, чтобы приостановить его, а затем CONT для продолжения.

Применение:

 kill -STOP <pid> kill -CONT <pid> 
  • Mount dev, proc, sys в среде chroot?
  • Извлечение файла tar.gz возвращает: «Это не похоже на архив tar».
  • UnionFS одинаково в окнах, фактически объединять папки
  • Что означает «Роуминг, не разрешенный сервером» для клиента ssh?
  • Измерение времени выполнения скрипта
  • Есть ли практическая причина для Linux с двойной загрузкой вместе с Windows?
  • Как установить больше строк для прокрутки назад, в текстовом режиме?
  • Программа mime-типа по умолчанию несовместима между системой и mozilla firefox / thunderbird?
  • Список содержимого tarball в формате дерева
  • Каковы недостатки использования UEFI-загрузки?
  • Как открыть приложение при запуске X session
  • Давайте будем гением компьютера.