Последние выпуски sudo добавили новые возможности, которые позволяют отслеживать и контролировать ранее скрытые проблемные области.
Когда вы хотите предоставить административный доступ некоторым пользователям, контролируя и проверяя, что они делают на ваших системах, вы используете sudo. Однако даже при использовании sudo существует довольно много скрытых возможностей - стоит подумать о предоставлении доступа к командной оболочке. В последних выпусках sudo добавлены функции, позволяющие видеть эти моменты и даже контролировать их. Например, вы можете включить более подробные и удобные для обработки сообщения журнала и регистрировать каждую команду, выполняемую в сеансе командной оболочки.
Некоторые из этих функций являются совершенно новыми. Некоторые из них основаны на функциях, появившихся в версии 1.9.0 или даже раньше. Например, sudo мог записывать все, что происходило на терминале, даже в версии 1.8. Однако система хранила эти записи локально, и их было легко удалить, особенно в тех случаях, когда эти записи были наиболее полезны: Shell-сессии. Версия 1.9.0 добавила централизованный сбор записей сеансов, поэтому записи не могут быть удалены локальным пользователем, а в последних версиях добавлены функции ретрансляции, что сделало сбор еще более надежным.
Первая новая функция, которую я хочу представить, это ведение логов в формате JSON. Когда она включена, sudo записывает гораздо больше информации и делает это в более удобном для анализа виде.
Традиционные сообщения syslog по sudo коротки и содержат лишь минимальное количество необходимой информации. Это связано с ограничениями старых реализаций syslog: Сообщения размером более 1kB отбрасывались или усекались:
Jan 28 13:56:27 localhost.localdomain sudo[10419]: user1 : TTY=pts/0 ; PWD=/home/user1 ; USER=root ; COMMAND=/bin/bash
Более современные реализации syslog могут обрабатывать сообщения гораздо большего размера. syslog-ng по умолчанию принимает сообщения журнала размером до 64kB (но, конечно, он может быть меньше или больше, в зависимости от фактической конфигурации).
Jan 28 13:58:20 localhost.localdomain sudo[10518]: @cee:{"sudo":{"accept":{"uuid":"616bc9efcf-b239-469d-60ee-deb5af8ce6","server_time":{"seconds":1643374700,"nanoseconds":222446715,"iso8601":"20220128125820Z","localtime":"Jan 28 13:58:20"},"submit_time":{"seconds":1643374700,"nanoseconds":209935349,"iso8601":"20220128125820Z","localtime":"Jan 28 13:58:20"},"submituser":"user1","command":"/bin/bash","runuser":"root","runcwd":"/home/user1","ttyname":"/dev/pts/0","submithost":"localhost.localdomain","submitcwd":"/home/user1","runuid":0,"columns":118,"lines":60,"runargv":["/bin/bash"],"runenv":["LANG=ru_RU.UTF-8","HOSTNAME=localhost.localdomain","SHELL=/bin/bash","TERM=xterm-256color","PATH=/home/user1/.local/bin:/home/user1/bin:/usr/local/bin:/usr/bin:/usr/local/sbin:/usr/sbin","MAIL=/var/mail/root","LOGNAME=root","USER=root","HOME=/root","SUDO_COMMAND=/bin/bash","SUDO_USER=user1","SUDO_UID=1000","SUDO_GID=1000"]}}}
Вы можете включить сообщения журнала в формате JSON в файле sudoers:
Defaults log_format=json
Еще одна функция, связанная с протоколированием, в версии 1.9.4 - сбор всех сообщений журнала sudo (включая сбои) с помощью sudo_logsrvd. До этого система записывала в журнал только успешные сессии, когда sudo_logsrvd фактически вел журнал. По умолчанию логирование по-прежнему осуществляется через syslog.
Почему это важно? Во-первых, вы можете собрать все, что связано с sudo, в одном месте, как записи сеансов, так и все соответствующие сообщения журнала. Во-вторых, это гарантирует правильное протоколирование всех событий, связанных с sudo, поскольку sudo может отказаться выполнять команды, если sudo_logsrvd недоступен.
Вы можете включить ведение журнала на sudo_logsrvd с помощью следующей настройки в файле sudoers (разумеется, замените IP-адрес):
Defaults log_servers=172.16.167.150
Если вы хотите получать сообщения журнала в формате JSON, вам нужно установить следующий параметр в разделе [eventlog] конфигурации sudo_logsrvd:
log_format = json
В противном случае sudo_logsrvd использует традиционный формат журнала sudo с простой модификацией. Кроме того, включается информацию о хосте, с которого получен журнал:
Nov 18 12:40:16 centos8test.localdomain sudo[21028]: user1 : 3 incorrect password attempts ; HOST=centos7sudo.localdomain ; TTY=pts/0 ; PWD=/home/user1 ; USER=root ; COMMAND=/bin/bash Nov 18 12:40:23 centos8test.localdomain sudo[21028]: user1 : HOST=centos7sudo.localdomain ; TTY=pts/0 ; PWD=/home/user1 ; USER=root ; TSID=00000A ; COMMAND=/bin/bash Nov 18 12:40:30 centos8test.localdomain sudo[21028]: user1 : command rejected by I/O plugin ; HOST=centos7sudo.localdomain ; TTY=pts/0 ; PWD=/home/user1 ; USER=root ; COMMAND=/bin/bash
Когда первоначально был представлен sudo_logsrvd (версия 1.9.0), для централизованного сбора записей сессий, клиенты могли отправлять записи только напрямую. В версии 1.9.7 была введена концепция ретрансляции. С помощью ретрансляторов вместо прямой отправки записей можно отправлять записи на несколько уровней промежуточных узлов, которые формируют вашу сеть.
Почему это важно? Во-первых, ретрансляция позволяет собирать записи сессий, даже если центральный узел недоступен из-за проблем с сетью или технического обслуживания. По умолчанию sudo отказывается запускаться, если не может отправить записи, поэтому использование ретрансляторов может гарантировать, что вы сможете использовать sudo в любое время суток.
Во-вторых, это также позволяет более жестко контролировать вашу сеть. Вместо того, чтобы открывать брандмауэр для всех хостов к центральному sudo_logsrvd, вам нужно разрешить только ваш ретранслятор.
Наконец, он позволяет собирать записи сессий из сетей без прямого доступа в интернет, например, из приватных сетей AWS, где вы можете установить sudo_logsrvd в режиме ретрансляции на хосте шлюза.
При использовании ретрансляторов настройка клиентов sudo и центрального sudo_logsrvd остается прежней. На хосте ретрансляции добавьте следующую строку в раздел [relay] файла sudo_logsrvd.conf:
relay_host = 172.16.167.161
Если известно, что сетевое соединение с центральным сервером проблематично, можно настроить ретранслятор на хранение записей перед их пересылкой:
store_first = true
Хотелось ли вам когда-нибудь узнать, что происходит в сеансе оболочки, запущенном через sudo? Да, записи сеансов существуют, но просматривать их часами, чтобы увидеть пару выполненных команд, скучно и большая трата времени. К счастью, в версии 1.9.8 появились подкоманды ведения журнала. Теперь достаточно регулярно проверять сообщения журнала и просматривать записи только тогда, когда происходит что-то подозрительное.
Вам даже не нужно правило, разрешающее доступ к оболочке, чтобы иметь доступ к оболочке, достаточно иметь доступ к редактору. Большинство редакторов могут запускать внешние команды. Мой любимый редактор - joe, и вот что вы можете увидеть, когда я запускаю его через sudo:
Aug 30 13:03:00 asuslaptop sudo[10150]: user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/joe
Ничего интересного, просто редактор - даже если я вызову оболочку и удалю несколько файлов и разделов из этой оболочки. Теперь давайте посмотрим, что произойдет, если включить подкоманды ведения журнала:
Aug 30 13:13:14 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/joe Aug 30 13:13:37 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/bin/sh -c /bin/bash Aug 30 13:13:37 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/bin/bash Aug 30 13:13:37 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/readlink /proc/10889/exe [...] Aug 30 13:13:37 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/sed -r s@/*:|([^\\]):@\1\n@g;H;x;s@/\n@\n@ Aug 30 13:13:37 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/tty Aug 30 13:13:42 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/id Aug 30 13:13:56 user1 : TTY=pts/1 ; PWD=/home/user1 ; USER=root ; COMMAND=/usr/bin/ls -A -N --color=none -T 0 /usr/share/syslog-ng/include/scl/
Я опустил десятки строк, чтобы сэкономить место, но вы все равно можете увидеть, что я запустил оболочку, и команды, выполняемые bash_profile, можно также увидеть в журналах.
Вы можете включить ведение журнала подкоманд в файле sudoers с помощью следующего параметра:
Defaults log_subcmds
В традиционных журналах sudo по идентификатору процесса sudo видно, что эти журналы относятся к одной и той же сессии sudo. Если вы включите ведение журналов в формате JSON, как было показано ранее, sudo будет записывать в журналы гораздо больше информации, что облегчит их анализ.
Протоколирование подкоманд устраняет большинство скрытых проблемных областей sudo, но бывают ситуации, когда вы хотите не просто наблюдать за происходящим, но и контролировать поток событий. Например, вам нужно предоставить пользователю доступ к командной оболочке, но при этом вы хотите запретить ему выполнять определенную команду. Перехват идеально подходит для таких случаев. Конечно, есть некоторые ограничения, например, вы не можете ограничить встроенные команды оболочки.
Допустим, команда who опасна. Вы можете включить перехват в два этапа. Первый включает его, второй - настраивает. В этом случае моему пользователю не разрешено запускать who:
Defaults intercept user1 ALL = (ALL) ALL, !/usr/bin/who
Вот что происходит, когда я запускаю сеанс командной оболочки root через sudo и пытаюсь запустить who:
$ sudo -s # who Sorry, user user1 is not allowed to execute '/usr/bin/who' as root on asuslaptop. bash: /usr/bin/who: Permission denied
Вы можете легко отключить запуск командных оболочек под sudo вообще:
Defaults intercept Cmnd_Alias SHELLS=/usr/bin/bash, /usr/bin/sh, /usr/bin/csh user1 ALL = (ALL) ALL, !SHELLS
Однако это также означает, что вы не можете запускать сеансы командной оболочки через sudo. Мало того, вы также не можете выполнять внешние команды из редакторов. Вот что происходит, когда я пытаюсь запустить команду ls из vi:
$ sudo vi /etc/issue Sorry, user user1 is not allowed to execute '/bin/bash -c /bin/ls' as root on asuslaptop. Cannot execute shell /bin/bash Press ENTER or type command to continue
Я надеюсь, что чтение этой статьи вызовет у вас желание попробовать эти новые возможности самостоятельно. Вы можете установить последнюю версию sudo на многие дистрибутивы Linux и UNIX из менеджера пакетов или использовать бинарный установщик, доступный на сайте Sudo.
В этой статье представлен лишь обзор новых возможностей. Если вы хотите узнать больше об этих возможностях, посетите веб-сайт, на котором размещены страницы с руководствами, а также блог Sudo.