Фактически являются программами `if` и` then`

Судя по тому, как я читал документацию, если вы используете ssh-agent , ssh-copy-id установит туда все ключи которые еще не работают, так что это должно работать (но я не тестировал):

# spawn a new agent for this so we know it's not keeping keys
$(ssh-agent)
# add keys
ssh-add new-key.pem old-key.pem
# check if those keys made it in
ssh-add -l
# and now add extra keys
ssh-copy-id user@remote
# stop the extra ssh-agent
kill $SSH_AGENT_PID
15
22.01.2017, 09:45
5 ответов

; разделяет утверждения (грубо говоря). (Почти) всегда можно заменить ; новой строкой.

Сказать, что ; разделяет две программы, поэтому , если и , то должны быть «программами», слишком упрощенно, поскольку утверждение может быть сделано из зарезервированные слова, функции оболочки, встроенные утилиты и внешние утилиты, а также их комбинации с использованием каналов, логических операторов и т. д. и т. д.

Оба if и , то являются зарезервированными словами в грамматика оболочки , а не «программы». Здесь они используются для создания того, что технически называется составной командой .

echo , вероятно, является встроенной утилитой в оболочке (но не обязательно), а ls , вероятно, является внешней утилитой (или «программой», как вы говорите).

27
27.01.2020, 19:49

, затем и else не являются программами. Остальные части есть. Обратите внимание, что непосредственно после них нет ; ', но после команды, которой они предшествуют.

[...] является командой и требует ; , если за ней следует начало другой команды.

AFAIK, все управляющие структуры в Bash и , вероятно, большинство * nix-оболочек, одинаковы. Это инструкции для переводчика. С другой стороны, тест или условие использует программу / процесс, которые «выполняются» и являются командами. Поскольку , то является частью строки, которая ведет к команде echo , она должна быть отделена новой строкой от предыдущей команды [...] . Его не нужно отделять от команды, которую он контролирует, echo yes .

С юридической точки зрения, хотя это некрасиво и трудночитаемо, вы тоже можете это сделать.

if [ $VARIABLE == abcdef ]
then echo yes
else echo no
fi

Обратите внимание, что здесь нет необходимости в ; между элементами управления, даже если они не на своей линии.

Интересно, что вся управляющая структура ( if ... fi ) является командой оболочки, и вся структура должна заканчиваться новой строкой или ; . Последняя строка не может быть fi echo done , но должна быть fi; эхо сделано . То же, что и присвоение VARIABLE = 'abcdef' , является командой.

Несмотря на то, что все управляющие структуры являются командами, они все же не являются программами.

2
27.01.2020, 19:49

Хотя это хорошее первое приближение, когда кто-то только начинает изучать основы использования оболочек, на уровне «вот как можно запускать программу «и» вот как можно запускать несколько программ одну за другой в одной строке », на самом деле это не так.

Сложнее понять новичку, но более правильное объяснение состоит в том, что язык оболочки - это компьютерный язык . Он имеет синтаксис . Этот синтаксис содержит различные лексические элементы , включая (среди прочего) символы новой строки, операторы, слова и зарезервированные слова.

if , , то , else и fi - все зарезервированные слова . Они имеют особое значение при синтаксическом анализе входных данных, передаваемых оболочке в соответствии с ее грамматикой . Аналогично, ; является оператором разделителя .

Таким образом, ввод на языке оболочки - это компьютерная программа, которая интерпретируется другой программой, интерпретатором , оболочкой.Его отдельные грамматические части не являются программами. Язык оболочки - это способ указания (других) программ для запуска оболочки.

[ не является специальным лексическим элементом в грамматике оболочки, например оператором. Это обычное слово , которым названа одна такая программа с именем [. Многие оболочки имеют встроенную версию этой программы, объединенную в код самой программы оболочки, но вы также можете найти внешнюю программу с этим именем где-нибудь, например, ] / bin / [ или / usr / bin / [, которые могут вызывать программы , кроме оболочки. Точно так же ] также не является специальным лексическим элементом оболочки. Обычное слово, которое становится аргументом для программы [. Программа [ требует, чтобы ее последний аргумент при выполнении был ] , который затем игнорируется.

Другая похожая программа, названная в вашем вопросе, - echo . Опять же, у большинства оболочек есть встроенная версия этой программы. Но, опять же, есть и внешняя версия программы, например, / bin / echo или / usr / bin / echo , для программ , отличных от оболочек. вызывать.

Третья программа, названная в вашем вопросе, - ls . Оболочки обычно не имеют встроенных версий этой программы, и это внешняя программа, которую можно найти где-нибудь, например, / bin / ls или / usr / bin / ls .

Для оболочки Bourne Again вы можете прочитать больше об этом в Основные функции оболочки документации по оболочке GNU Bourne Again. Другие оболочки, естественно, имеют другую грамматику.Единая спецификация Unix описывает синтаксис, которому должны соответствовать все POSIX-совместимые оболочки (в их POSIX-совместимых режимах).

Дополнительная литература

  • « Грамматика оболочки ». Командный язык оболочки . Базовые спецификации Выпуск 7. Открытая группа. IEEE 1003.1-2008. ISBN 1937218812.
  • тест . Утилиты . Базовые спецификации Выпуск 7. Открытая группа. IEEE 1003.1-2008. ISBN 1937218812.
  • « Грамматика оболочки ». Руководство Z Shell . версия 5.3.1. 2017.
7
27.01.2020, 19:49

if , elif , then и fi все зарезервированные ключевые слова, используемые для реализации одной из конструкций, называемых составной командой в оболочке, что означает, что в оболочке не может быть команды (или, скорее, другой команды) с любым из этих имен. Назначение ; в целом - не разделение команд, а завершение списка команд . Например, следующий допустимый оператор if :

if echo foo; echo bar; echo baz; then echo done; echo really done; fi

Условием оператора if является список команд echo foo; эхо-бар; echo baz . Синтаксический анализатор знает, что условие выполнено, потому что , затем , которое следует сразу за точкой с запятой, не может быть командой, потому что это зарезервированное ключевое слово. Таким образом, он знает, что то, что следует за , тогда является началом тела.Аналогично, fi является зарезервированным ключевым словом и, следовательно, не может быть третьей командой в теле оператора if , но отмечает конец составной команды.

1
27.01.2020, 19:49

На самом деле нет ничего удивительного в том, чтобы рассматривать if , , затем и else как внешние программы. Фактически, оболочка Томпсона в исходной 1-й редакции Unix реализовывала if и goto как внешние программы. Это возможно, потому что подпроцесс разделяет файловые дескрипторы с процессом оболочки, поэтому (вперед) goto просто нужно было читать ввод, пока он не найдет целевую метку, а затем завершится. См. оболочка Томпсона .

5
27.01.2020, 19:49

Теги

Похожие вопросы