ПРИМЕЧАНИЕ. Это в основном программа (сценарий оболочки), которую я создал, и я знаю, что этот форум - скорее сайт с вопросами и ответами, чем сайт, посвященный ознакомлению с программами. Но у меня нет какой-либо учетной записи GitHub (или аналогичной), и у меня не было времени исследовать метод публикации программы с открытым исходным кодом для сообщества. Таким образом, до тех пор, пока существует риск, что работающая и полезная программа останется незамеченной (даже в течение нескольких месяцев) для тех, кто может ею пользоваться, и было бы грустно не делиться уже созданной программой, я собираюсь опубликовать ее здесь для сейчас. Для меня не проблема, если администраторы решат удалить эту ветку, я пойму. Я надеюсь сформулировать вопрос в форме вопроса-ответа, чтобы сделать его полезным для этого форума. Если заинтересованных пользователей будет достаточно, я сделаю все возможное, чтобы посвятить некоторое время продолжению проекта (после всех моих исследований я не нашел ничего похожего на это в Интернете, но, ну ... Я не знаю, является ли мой сценарий ценным или это была пустая трата времени).
Я запрограммировал простой скрипт оболочки Linux, который работает (до сих пор) в CygWin и помогает (я надеюсь) сократить интервал атаки SUDO для CygWin. Программа называется TOUACExt (аббревиатура от « TimeOut и расширение UAC ») и действует как оболочка для SUDO для CygWin (обязательно установлена) и действительно состоит из набора из четырех программ .sh
.
Особенности:
- Удобное использование . При моделировании исходного sudo из поведения Linux приглашение запроса подтверждения UAC появляется только один раз (несколько последовательных команд
sudo
будут генерировать только один запрос UAC). Пока sudoserver.py продолжает работать (по умолчанию 15 минут), запросов UAC больше не будет.
- Привилегированные (Admin) пользователи получают только запрос подтверждения UAC (Да / Нет) на экране.
- Непривилегированные (не администраторы) пользователи получают экран ввода учетной записи администратора / пароля .
- Файл sudoserver.py продолжает работать, а затем автоматически закрывается через заданное время (15 минут) с момента последнего выполнения команды sudo.
- sudoserver.py не закрывается (продолжает работать и проверит снова через 5 минут) в случае запуска sudo .
- Работает удаленно (проверено через SSH):
- Непривилегированные пользователи не могут запускать sudoserver.py удаленно.
- Создает (но простой и не очень читаемый) журнал в
/var/log/SUDOForCygWin/
.
Требования (в CygWin):
- SUDO для CygWin.
- pgrep (в пакете
procps
).
- flock (в пакете
util-linux
).
- nohup (я думаю, установлен по умолчанию на CygWin, но не уверен).
Предполагая:- две программы проекта SUDO for CygWin по пути, предложенному автором:
/usr/local/bin/sudoserver.py
/usr/local/bin/sudo
TOUACExt был протестирован, работая на Windows 7 SP1 и Windows XP SP3, но я не знаю, имеет ли смысл использовать его на последнем.
Инструкция по установке:
Поместите этот скрипт (предлагаемое имя: SUDOServer.cmd
) и создайте ярлык (вы можете персонализировать его значок, если хотите) для него с именем SUDOServer.lnk
(вы должны включить на этом ярлыке Advanced Options --> Execute as Administrator
) в любом месте вашего Путь к Windows, поэтому sudoserver.py
можно напрямую запросить из Windows:
c:\CygWin\bin\python2.7.exe /usr/local/bin/sudoserver.py
Поместите четыре .sh скрипта TOUACExt в путь, например:
/usr/local/bin/SUDO.sh
/usr/local/bin/SUDOServer.sh
/usr/local/bin/SUDOServerWatchDog.sh
/usr/local/bin/SUDOServerWatchDogScheduler.sh
Переименуйте оригинальный скрипт Python из sudo
в sudo.py
:
mv /usr/local/bin/sudo /usr/local/bin/sudo.py
ВНИМАНИЕ: Оригинальный сценарий Python "sudo" не должен оставаться нигде в вашем пути, или он может быть выполнен вместо этого.
Создайте этот псевдоним (например, вручную или отредактировав ваш ~/.bashrc
):
alias sudo='SUDO.sh'
Код для СУДО.ш:
#!/bin/bash
# ********** SUDO.sh v0.04a **********
# Variables:
# LockFile (will use a temporal one for now):
#lockfile=sudoserver-running.lck
LockFile=lockfile.lck
# Creating LogFile (if it does not exist):
mkdir /var/log/SUDOForCygWin 2>/dev/null
chmod 777 /var/log/SUDOForCygWin 2>/dev/null
LogFile=/var/log/SUDOForCygWin/$(date +%Y%m%d).log
exec 5>>$LogFile # Redirector 5 will be the log file.
chmod 777 $LogFile >&5 2>&5 # Writable to anyone (for now).
# Start of the program
echo "========== Starting SUDO Server for CygWin ==========" >&5
echo $(date) >&5
# does the lock file exists as locked?
if [ $(flock -n $TMP/$LockFile echo>/dev/null;echo $?) -eq 0 ]
then
# The lock file is not locked.
echo "LockFile not locked. Testing sudo access..." >&5
if [ $(sudo.py vartemp=0>/dev/null 2>/dev/null;printf $?) -eq 0 ]
then
# Wooops. sudoserver.py is running without the lockfile. Better to correct this.
echo "LockFile not locked, but sudoserver.py seems to be running." >&5
printf "Killing sudoserver.py...\n" >&5
sudo.py kill $(sudo.py pgrep.exe -f -l sudoserver.p[y] | grep "pgrep" -v | awk '{print $1}') >&5 2>&5
fi
# Starting SUDOServer.sh
printf "Requesting SUDOServer start...\n" >&5
nohup SUDOServer.sh >&5 2>&1&
# Wait some time delay for UAC Prompt to start
sleep 2
timeout=$((SECONDS+10))
# Has sudoserver.py already started?
while [ $(flock -w 1 $TMP/$LockFile echo>/dev/null;printf $?) -eq 0 ] || [ $(tasklist | grep "consent.exe" -i>/dev/null;printf $?) -eq 0 ]
do
# No. We have to wait.
# Waiting for SUDOServer.py to be running.
printf "."
if [ $SECONDS -ge $timeout ]
then
# sudoserver.py not responding. Aborting with errorlevel=3.
printf "sudoserver.py not responding. Aborting.\n"
exit 3
fi
done
# Yes. sudoserver.py is up and running.
fi
printf "\n"
# Schedule (add) SUDOServer Watch Dog to Task Scheduler:
SUDOServerWatchDogScheduler.sh
# Invoke requested sudo command
sudo.py $@
#printf "ErrorLevel was: "$?
# ErrorLevel Codes:
# 3 --> timeout waiting for sudoserver.py to respond.
Код для SUDOServer.sh:
#!/bin/bash
# ********** SUDOServer.sh v0.04a **********
# Variables:
# LockFile (a temporal one for now):
#lockfile=sudoserver-running.lck
LockFile=lockfile.lck
# Check for other instances of sudoserver.py running
if [ $(flock -n $TMP/$LockFile echo>/dev/null;printf $?) -eq 0 ]
then
printf "Creating lockfile: "$TMP/$LockFile"\n"
flock $TMP/$LockFile -c 'cmd /c SUDOServer'
# The file has been unlocked. Send error level=2.
exit 2
else
printf "The lockfile: "$TMP/$LockFile" is locked by another process.\n"
printf "Exiting SUDOServer.sh"
fi
printf "SUDOServer.sh execution finished. Exiting."
# Exiting with no problems.
exit 0
# ErrorLevel Codes:
# 2 --> SUDOServer.lnk (maybe denial of UAC).
Код для SUDOServerWatchDog.sh:
#!/bin/bash
# ********** SUDOServerWatchDog.sh v0.04a **********
# Variables:
# LockFile (a temporal one for now):
#lockfile=sudoserver-running.lck
LockFile=lockfile.lck
# Redirecting to LogFile:
LogFile=/var/log/SUDOForCygWin/$(date +%Y%m%d).log
exec 5>>$LogFile
if [ $(stat $LogFile -c %a) -ne 777 ]
then
echo "Logfile "$LogFile" has incorrect permissions." >&5
echo "Attemping to change permissions of "$LogFile >&5
chmod 777 $LogFile >&5 2>&5
fi
# Remove Task Scheduler entry, if exists.
if [ $(schtasks.exe /query | grep "SUDOServerWatchDog" -i>/dev/null 2>&5;printf $?) -eq 0 ]
then
sudo.py schtasks.exe /delete /tn "SUDOServerWatchDog" /f >&5 2>&5
fi
# Is sudoserver.py running?
if [ $(flock -n $TMP/$LockFile echo>/dev/null;printf $?) -eq 1 ] || [ $(sudo.py vartemp=0>/dev/null 2>/dev/null;printf $?) -eq 0 ]
then
# Yes. sudoserver.py is running. So...
printf "sudoserver.py detected running...\n" >&5
# Is any instance of sudo running right now?
if [ $(sudo.py pgrep -f -l "/usr/local/bin/sudo.py " | grep -v grep>/dev/null 2>&5;printf $?) -eq 0 ]
then
# Yes. sudo is running right now. So...
printf "There are instances of sudo running.\n" >&5
sudo.py schtasks /create /tn "SUDOServerWatchDog" /tr "SUDOServerWatchDog" /sc minute /mo 5 /sd 10/10/2010 /ru "SYSTEM" >&5 2>&5
printf "Will check again in 5 minutes. Adding Task.\n" >&5
else
# No. sudo is not running right now. So...
# Kill sudoserver.py.
printf "Closing sudoserver.py\n" >&5
sudo.py kill $(sudo.py pgrep.exe -f -l sudoserver.p[y] | grep "pgrep" -v | awk '{print $1}')
fi
else
printf "sudoserver.py not running. Nothing to be done.\n" >&5
fi
Код для SUDOServerWatchDogScheduler.sh:
#!/bin/bash
# ********** SUDOWatchDogScheduler.sh v0.04a **********
# Check if WatchDog is already scheduled
if [ $(schtasks.exe /query | grep "SUDOServerWatchDog">/dev/null 2>&5;printf $?) -eq 0 ]
then
# Yes. Remove it in order to create a new one.
echo "Task SUDOServerWatchDog already existing." >&5
echo "Removing task SUDOServerWatchDog..." >&5
sudo.py schtasks.exe /delete /tn "SUDOServerWatchDog" /f >&5 2>&5
if [ $? -eq 0 ]
then
# Task correctly deleted.
echo "Task correctly removed." >&5
else
# Something failed in task creation. Report.
echo "ERROR on deleting the SUDOServerWatchDog programmed task." >&5
fi
fi
# Schedule new task for deletion.
echo "Adding new SUDOServerWatchDog task to trigger in 15 minutes." >&5
sudo.py schtasks /create /tn "SUDOServerWatchDog" /tr "SUDOServerWatchDog" /sc minute /mo 15 /sd 10/10/2010 /ru "SYSTEM" >&5 2>&5
if [ $? -eq 0 ]
then
# Task correctly scheduled.
echo "Task SUDOServerWatchDog correctly scheduled." >&5
else
# Something failed in task scheduling. Report.
echo "ERROR on scheduling programmed task SUDOServerWatchDog." >&5
fi
Протестируйте программу из оболочки CygWin Bash:
Luis@Kenobi ~
$ sudo ls -la
<UAC ELEVATION PROMPT APPEARS>
total 49
drwxr-xr-x+ 1 Luis None 0 abr 7 02:23 .
drwxrwxrwt+ 1 Luis- None 0 abr 4 03:27 ..
-rw------- 1 Luis None 13798 abr 14 00:31 .bash_history
-rwxr-xr-x 1 Luis None 1494 mar 3 11:36 .bash_profile
-rwxr-xr-x 1 Luis None 6260 abr 6 05:19 .bashrc
-rwxr-xr-x 1 Luis None 1919 mar 3 11:36 .inputrc
-rw------- 1 Luis None 35 abr 2 01:43 .lesshst
-rwxr-xr-x 1 Luis None 1236 mar 3 11:36 .profile
drwx------+ 1 Luis None 0 mar 8 01:49 .ssh
-rw-r--r-- 1 Luis None 7 mar 4 18:01 d:ppp.txt
-rw-r--r-- 1 Luis None 37 abr 7 02:23 my.log
ПРИМЕЧАНИЕ 2. Эти сценарии находятся в предварительной бета- версии, поэтому они все еще содержат ошибки и код не очень чистый. Во всяком случае, в моих тестах на трех разных компьютерах с Windows 7 они работали (в основном) нормально.
Краткое описание программы:
- Из-за псевдонима при выполнении команды sudo вызывается сценарий SUDO.sh.
- SUDO.sh вызывает SUDOServer.sh, открывая (через
SUDOServer.lnk
) «sudoserver.py», если необходимо.
- Исходная команда sudo, вызываемая пользователем, выполняется.
- Затем SUDO.sh вызывает SUDOServerWatchDogScheduler.sh, который планирует выполнение SUDOServerWatchDog.sh по истечении заданного времени (по умолчанию 15 минут), чтобы закрыть
sudoserver.py
.
- По истечении заданного времени SUDOServerWatchDog.sh закрывает sudoserver.py . Если есть какой-либо запущенный экземпляр sudo, он запрограммирует себя на новое выполнение через 5 минут.
Делать:
- Само инсталлятор , который создает все .sh, CMD и .lnk файлы автоматически.
- Установите файл блокировки для другого (он находится в $ TMP/lockfile.lck).
- Добавьте сценарий конфигурации или файл .config (для значений по умолчанию в тайм-аутах, расположениях файлов ... и т.д.).
- Добавить поведение учетной записи системы (спасибо, @ Wyatt8740).
- ¿Заменить "flock" (режим внутренней блокировки SUDO) на "fuser", где это уместно?
- Предложения принимаются.
Сообщенные ошибки:
- Оболочка bash остается открытой даже после ввода команды
exit
если sudoserver.py
работает, пока не закроется. Предварительные обходные пути приветствуются.
Я надеюсь, что кто-то будет использовать многочасовое программирование, которое я посвятил TOUACExt.
Улучшения и исправления приняты.
Предложения о том, куда я должен пойти, публикуя код, чтобы прекратить ворчать на этом форуме, тоже принимаются ;-).
Простите за длинный пост. У меня не так много свободного времени, и этот проект вот-вот исчезнет у меня в шкафу (может, на долгие годы, кто знает?).