Где определена оболочка входа?

16

Я читал разницу между sudo -i/-s здесь . После использования команды shoptотмечается, что все ( sudo su/sudo -i/sudo -s) $SHELLпредоставляют одинаковые результаты, но shoptрезультаты команды разные.

Итак, как определяется логин и не логин оболочки?

Откуда shoptвзять результат?

Почему это не связано с $SHELL?

судо су

givinv@87-109:~$ sudo su
root@87-109:/home/givinv# 
root@87-109:/home/givinv# 
root@87-109:/home/givinv# shopt -q login_shell && echo 'Login shell' || echo 'No login shell'
No login shell
root@87-109:/home/givinv# echo $SHELL
/bin/bash
root@87-109:/home/givinv# 
root@87-109:/home/givinv# exit
givinv@87-109:~$ 

судо

givinv@87-109:~$ sudo -i
root@87-109:~# 
root@87-109:~# shopt -q login_shell && echo 'Login shell' || echo 'No login shell'
Login shell
root@87-109:~# echo $SHELL
/bin/bash
root@87-109:~# 

судо

root@87-109:~# sudo -s
root@87-109:~# shopt -q login_shell && echo 'Login shell' || echo 'No login shell'
No login shell
root@87-109:~# echo $SHELL
/bin/bash
root@87-109:~# 
Prado
источник
7
Одна проблема заключается в том, что «оболочка входа в систему» ​​имеет два значения: 1. Это экземпляр оболочки, запущенной особым образом, которая выполняет определенные действия (например, чтение .profileили эквиваленты), и 2. Это оболочка, которая должна запускаться при входе в систему для пользователь, как определено в /etc/passwdили эквивалентный. $SHELLсодержит последнее, ваши shoptвыходы имеют дело с первым. Обычно, когда оболочка в (2) запускается при входе в систему, она запускается особым образом, необходимым для (1), следовательно, происходит слияние значений.
Муру
1
Объяснение @muru хорошее. например, если вы используете SSH на своем компьютере с удаленного компьютера. / usr / sbin / sshd в вашей системе может создать оболочку, определенную $SHELL(и подключить ее к псевдотерминалу), которая, в свою очередь, определена в вашей записи / etc / passwd. эта оболочка является оболочкой входа в систему и может быть протестирована с if [[ -o login ]]; then echo "I am a login shell"; fi. будучи оболочкой входа в систему, он будет выполнять те задачи, которые соответствуют новому сеансу. например, источник ~/.zprofileили аналог, который, возможно, установит переменные окружения и любой пользовательский код оболочки, который вы можете захотеть запустить в это время
the_velour_fog

Ответы:

17

TL; DR :

  • Где определена оболочка входа? В /etc/passwd.
  • А sudo su/ sudo su -/ sudo -i/ то sudo -sже самое? Нет, все они порождают раковину, но по-разному и в разных контекстах.
  • Что делает $SHELL? Просто укажите вашу оболочку по умолчанию, так же, как и в /etc/passwd.

Фактический ответ :

Прежде всего, важно упомянуть, что shoptэто специфично для bash. Например, я являюсь mkshпользователем оболочки, и его нет shopt, как kshнет.

Далее, что именно login_shellдолжно представлять? От man bash:

login_shell

Оболочка устанавливает эту опцию, если она запускается как оболочка входа

Это ключевой момент. sudo -iКак вы уже знаете из предыдущего прочитанного вами ответа, предполагается имитировать первоначальный вход в систему. Вот почему shoptотчеты login_shell on по этой опции. Думайте об этом так, как будто sudo -iвынуждает оболочку проходить через файлы, которые должны появляться только во время входа в систему (которые не получают из интерактивных оболочек).

В других случаях вы уже запускаете экземпляр оболочки, поэтому он не может быть оболочкой входа, во-первых, и назначение параметров другое. sudo -sпросто читает $SHELL(которая предназначена для представления вашей оболочки по умолчанию, как установлено /etc/passwd) и запускает ее с привилегиями root. Это эквивалентно выполнению sudo $SHELLили sudo mkshили sudo bash(в зависимости от того, что вы используете).

Помните, я упоминал, что я mkshпользователь? Взгляните на это:

$ bash --posix
bash-4.3$ sudo -s
[sudo] password for xieerqi: 

DIR:/xieerqi|01:53|skolodya@ubuntu:
$ id 
uid=0(root) gid=0(root) groups=0(root)

DIR:/xieerqi|01:53|skolodya@ubuntu:
$ echo $-
imsU

То, что вы видите, это то, что sudo -sвыскочил из bashмоей mkshоболочки с характерным для меня приглашением. И, конечно же, поскольку это не действие входа в систему, bashоно сообщило бы, что оболочка порождена как экземпляр оболочки без входа в систему. В моем случае, однако, вы видите, что $-там нет буквы l, которая была бы там, если бы это был экземпляр оболочки входа в систему.

Наконец, та же идея относится sudo suи к sudo su -. Позже один порождает экземпляр оболочки входа в систему (т. Е. Будут запускаться определенные файлы, необходимые для входа в систему), а первый порождает только интерактивные оболочки (т. Е. Файлы входа в систему не запускаются).

bash-4.3$ sudo su
[sudo] password for xieerqi: 
root@eagle:/home/xieerqi# shopt login_shell
login_shell     off
root@eagle:/home/xieerqi# exit
bash-4.3$ sudo su -
[sudo] password for xieerqi: 
$ shopt login_shell
login_shell     on

Так что технически shopt login_shellне имеет никакого отношения к $SHELLчему бы то ни было. Подумайте об этом так: его цель - показать, как работает bash. $SHELLдолжен отражать только то, что вы назначили в /etc/passwd.

Что касается различий между оболочкой входа в систему и оболочкой без регистрации, то в этом ответе она была объяснена уважаемым Жилем на unix.stackexchange.com .


Дополнительное веселье

Вот кое-что интересное, что вы можете попробовать. Как вы, возможно, уже знаете, будет запущена оболочка входа в систему .profile.bashrcпоскольку Ubuntu .profile настроена для этого ), но ад, не входящий в систему, будет запускать только .bashrcфайл. Таким образом, мы можем проверить, с echoкакой из этих команд запускается оболочка входа в систему, а какая нет, и мы ожидаем две строки echoдля оболочки входа в систему и только одну строку для отсутствия входа в систему.

$ echo "echo 'hi,i am .profile'"  >> .profile
$ echo "echo 'hi, i am .bashrc'" >> .bashrc
$ sudo -i
hi, i am .bashrc
hi,i am .profile
$ sudo su
hi, i am .bashrc
root@eagle:~# sudo su -
hi, i am .bashrc
hi,i am .profile
$ sudo -s
hi, i am .bashrc
root@eagle:~# 

Соответственно, те с двумя строками вывода будут login_shellустановлены в on.

Сергей Колодяжный
источник
Спасибо @Serg и @Zanna. Теперь об этом $SHELLи login_shell/non-login_shellуточнили. Но откуда shoptвзять подробности? Это из echo $0?
Прадо
1
@prado Я бы сказал, да, поскольку первый символ $0используется для обозначения того, является ли оболочка оболочкой входа в систему, поэтому, если shoptбы проверить эту переменную - конечно, это вполне приемлемо. Тем не менее, есть, вероятно, больше, чем кажется на первый взгляд. shoptвероятно, на этот вопрос у меня нет точного ответа, так как я не очень хорошо знаком с исходным кодом bash.
Сергей Колодяжный
@prado Bash можно запустить как оболочку входа в систему, указав в качестве первого символа $ 0 -или используя -lопцию.
Муру
@prado вы можете прочитать о вызове и опциях bash на странице руководства. например, в разделе «SHELL BUILTIN COMMAND» говорится, login_shell The shell sets this option if it is started as a login shell (see INVOCATION above). The value may not be changed.что, shopt login_shellпохоже, bash позволяет вам узнать - программно, как узнать, как он был запущен. другой путь был бы[[ -o login ]]
the_velour_fog
11

Как @Serg объясняет в этом ответе о том, как определить, какую оболочку вы используете , SHELLпеременная - это просто оболочка текущего пользователя по умолчанию, считанная из /etc/passwd:

$ grep zanna /etc/passwd
zanna:x:1000:1000:Zanna,,,:/home/zanna:/bin/bash

так что, если я echo $SHELLэто всегда будет возвращать /bin/bash:

$ zsh
% echo $SHELL
/bin/bash

Будь или не оболочка является Войти оболочки, является ш флигель неавтоматического ионов определяется в момент запуска оболочки. Программа оболочки хранит эту информацию вместе со всеми другими настройками и переменными. Команда shoptпредоставляет способ просмотреть эту информацию и, если возможно, для рассматриваемой опции, установить или отменить ее (это не тот случай, для login_shellкоторого, конечно, зависит от процесса, используемого для запуска оболочки)

Параметры sudoпрограммы определяют, как будут запускаться эти различные типы корневой оболочки:

введите описание изображения здесь

Занна
источник
1
Хорошее объяснение. Я думаю, что вы объяснили, что shoptи login_shellдолжны представлять гораздо лучше, чем в моем ответе.
Сергей Колодяжный
@Serg спасибо :) Я думаю, что ваше объяснение более тщательное :)
Zanna
3

man bash:

Оболочка входа - это тот, чей первый символ аргумента ноль равен a -, или тот, который начинается с --loginопции.

man login:

Значение для $HOME, $SHELL[...] устанавливается согласно соответствующим полям в вводе пароля.

Короче говоря:

  • Оболочка - это оболочка входа в систему, если она была вызвана как оболочка входа в систему.
  • Переменная окружения $SHELLустанавливается login, например, вызывающей или вызывающей программой su. Сама оболочка не устанавливает его.
  • shopt показывает параметры оболочки в настоящее время в силе.
AlexP
источник