Судо Ренис в питоне
В общем, это хороший вопрос. Linux не позволяет непривилегированным пользователям снижать привлекательность PID, и запускать все с правами root - это возможность для червей.
Тем не менее, вот мои особенности: у меня есть учетная запись пользователя, которая управляет несколькими процессами, который имеет пароль sudo
привилегии для renice
и несколько других команд, которые он использует. У меня также есть скрипт, который является общей точкой входа для всех пользователей в этой системе. Этот скрипт может запускать как обычные пользовательские программы, так и процессы, управляемые специальной учетной записью. Таким образом, скрипт при запуске с определенной опцией должен renice
если он может, но молча терпит неудачу, если не может.
Код, который я получил для этого, выглядит так:
subprocess.Popen(["sudo", "renice", "-20", str(process.pid)],
# shell = True,
stdout = subprocess.DEVNULL,
stderr = subprocess.STDOUT)
Если у меня есть shell = True
закомментировано, процесс приобретает новую привлекательность, но если я работаю как непривилегированный пользователь, sudo
выбрасывает запрос на ввод пароля и портит вывод моего терминала. Нажатие клавиш становится невидимым, и все выглядит глупо. Если я раскомментирую shell = True
Я не получаю вывод терминала. Однако процесс не меняет свою привлекательность, даже если я запускаю его как root.
Поврежденный вывод терминала вполне может быть связан с эмулятором терминала, который я использую (не пробовал его с другим), но я хочу объединить эти варианты поведения. Тишина от sudo
несмотря ни на что, но приятность изменится, если пользователь может успешно выполнить sudo.
Есть указатели?
1 ответ
Я думаю это потому что sudo
требуется TTY, даже если пароль не требуется.
Попробуйте предоставить один:
import os
import pty
import subprocess
master, slave = pty.openpty()
p = subprocess.Popen(
["sudo", "id", "-a"],
stdin=slave, stdout=slave, stderr=slave
)
os.close(slave)
output = os.read(master, 1026)
os.close(master)
print(output)
Код выше должен напечатать что-то вроде uid=0(root) gid=0(root) groups=0(root)
, Если это так, то заменить id
с renice
удали ненужное os.read
и тебе должно быть хорошо.
Обновление: в случае с OP он потерпел неудачу по другой причине. Добавление start_new_session=True
в Popen
он молча провалился для непривилегированных пользователей и преуспел в качестве пользователя root.