Почему “ls” требует отдельного процесса для выполнения?

Это - известная ошибка, FS#32423: emacsclient последовательно разрушает emacs. Об ошибке сообщили авторам Emacs. Это составлено ошибкой Gtk. Следующие обходные решения, как сообщают, работают:

  • Понижение до Emacs 24.1 (вместо 24,2).
  • Понижение бойкого к 2,32 (вместо 2,34).
  • Компиляция Emacs без Gtk (--with-x-toolkit=lucid).
  • Запуск демона без X доступных соединений (попытка DISPLAY= emacs --daemon).

Никакое фактическое решение, кажется, не известно в это время.

Это не что-то, что можно зафиксировать самостоятельно, если Вы не программист, и Вы знакомы с включенными технологиями. Ваш лучший выбор состоит в том, чтобы использовать одно из обходных решений и продолжать смотреть отчеты об ошибках за фиксацией.

14
10.01.2014, 07:05
6 ответов

Ответ - более или менее это ls внешний исполняемый файл. Вы видите его местоположение путем выполнения type -p ls.

Почему не ls встроенный в оболочку, затем? Ну, почему это должно быть? Задание оболочки не состоит в том, чтобы охватить каждую доступную команду, но обеспечить среду, способную к выполнению их. Некоторые современные оболочки имеют echo, printf, и их род как builtins, которые не должны технически быть builtins, но сделаны так по причинам производительности, когда они выполняются неоднократно (прежде всего, в жестких циклах). Не делая их builtins, оболочка должна была бы разветвиться и должностное лицо новый процесс для каждого вызова им, которые могли быть чрезвычайно медленными.

По крайней мере, выполнение ls, внешний исполняемый файл, требует выполнения одного из семейства должностных лиц системных вызовов. Вы могли сделать это без разветвления, но оно заменит основную оболочку, которую Вы используете. Вы видите то, что происходит в том экземпляре путем выполнения следующего:

exec ls; echo "this never gets printed"

Так как образ процесса Вашей оболочки заменяется, текущая оболочка больше не доступна после выполнения этого. Чтобы оболочка смогла продолжить бежать за выполнением ls, команда должна будет быть встроена в оболочку.

Разветвление позволяет замену процесса, который не является Вашей основной оболочкой, что означает, что можно продолжить выполнять оболочку впоследствии.

18
27.01.2020, 19:50
  • 1
    я думаю, что он спрашивает, почему ls (1) не является встроенной функцией оболочек, которые кто-то должен был бы объяснить, как у различных поставщиков есть различные варианты для ls (1) и способный запросить другой материал от файловой системы и т.д. И также взлеты и главным образом холмы наличия его 'встроенный' оболочка. –  llua 10.01.2014, 05:55
  • 2
    @llua я добавил некоторую информацию об этом и случаи исключения echo, printf, и т.д. обновленный вопрос –  Chris Down 10.01.2014, 06:00
  • 3
    Не всегда ясно, почему некоторыми вещами является builtins, и другие не. Например, почему cd не внешний исполняемый файл? –  Faheem Mitha 10.01.2014, 10:04
  • 4
    @FaheemMitha Там является внешним cd исполняемый файл в совместимых POSIX операционных системах (см. здесь). Если Вы хотите на самом деле chdir () в текущем процессе, тем не менее, необходимо было встроить его в оболочку. –  Chris Down 10.01.2014, 10:30
  • 5
    это стало привычкой почему ls является внешним, но это может быть также реализовано в оболочке. См. busybox. –   12.01.2014, 01:30

Состояния Справочника Bash:

Встроенные команды необходимы для реализации функциональности, невозможной или неудобной для получения с отдельными утилитами.

Таким образом, оболочки разработаны, чтобы только включать встроенные команды если:

  1. Требуемый стандартом POSIX
  2. Команды, которые требуют доступа к самой оболочке, такой как созданное-ins управление заданиями
  3. Команды, которые очень просты, не зависимы от операционной системы и эффективность выполнения увеличения при реализации столь же созданный-ins, такие как printf

ls команда не соответствует ни одному вышеупомянутому requirments.

Однако вот не ограничение программирования, которое предотвратило бы ls будучи implmented как встроенное, которое выполняется в том же процессе как интерпретатор удара. Причины дизайна команд, не являющихся implmented как созданная-ins оболочка:

  1. Оболочка должна быть быть отдельной от файловой системы - никакие встроенные команды не должны зависеть от корректной операции никакой файловой системы или периферийных устройств
  2. Команда, которая могла бы быть типом файловой системы или зависимый от операционной системы, должна быть отдельным исполняемым файлом
  3. Команда, от которой Вы могли бы хотеть передать по каналу к или, должна быть отдельным процессом
  4. Команда, которую Вы могли бы хотеть выполнить в фоновом режиме, должна быть отдельным исполняемым файлом
  5. Команда, которая имеет большое количество возможных параметров, лучше реализована в отдельном исполняемом файле
  6. Команды, которые должны иметь тот же вывод, независимо от которого тип оболочки (удар, csh, tsh...) вызывает их, должны быть автономными исполняемыми файлами

Относительно первой причины - Вы хотите, чтобы оболочка была максимально независима и эластична. Вы не хотите, чтобы оболочка застряла на ls из NFS монтируют, что это "не отвечает, все еще пробуя".

Относительно второй причины - Во многих экземплярах Вы могли бы хотеть использовать оболочку для системы, которая использует Busybox или другую файловую систему, которая имеет другое ls реализация. Или даже используйте тот же источник оболочки в ОС, которые имеют отличающийся ls реализации.

Относительно третьей причины - Для выражения такой как find . -type d | xargs ls -lad это было бы трудно или невозможно реализовать ls в том же процессе как интерпретатор оболочки.

Относительно четвертой причины - Некоторые ls команды могут занять много времени для завершения. Вы могли бы хотеть, чтобы оболочка продолжила выполнение чего-то еще тем временем.


Примечание: См. это полезное сообщение Warren Young в ответ на подобный вопрос.

15
27.01.2020, 19:50
  • 1
    Вы пропустили простоту передачи по каналу вывода, если бы это - отдельная команда, и все программирование его взяло бы для передачи по каналу оболочки, примитивной в отдельный исполняемый файл. –  Bruce Ediger 10.01.2014, 15:27
  • 2
    @BruceEdiger: Какое удовольствие получить комментарий от уважаемого БЫТЬ.Спасибо! Я полагаю, что обосновывают 3 покрытия Ваш комментарий, нет? –  Jonathan Ben-Avraham 10.01.2014, 15:30
  • 3
    я думал больше вроде того, насколько сложный исходный код самой оболочки был бы то, если бы это должно было обработать каналы для внешних процессов и передать вывод по каналу внутренняя команда как гипотетическое ls во внешний процесс. Это могло быть сделано, но это будет сложно. –  Bruce Ediger 10.01.2014, 19:06
  • 4
    я боюсь большинство, если не все Ваши 5 точек спорны. 1: ls (надо надеяться), независим от реализации файловой системы. Это до ядра, чтобы предоставить последовательный интерфейс стандартной библиотеке и приложениям. 2: ls, вероятно, меньше зависит к ОС, чем оболочка. 3: оболочки определенно позволяют builtins в конвейерах. 4: оболочки определенно позволяют builtins быть выполненным в фоновом режиме. 5: это довольно субъективно. –  jlliagre 10.01.2014, 19:32
  • 5
    @JonathanBen-Avraham @BruceEdiger, оболочки уже не обрабатывают случай канала для builtins с подоболочками? например, bash вывод alias | grep ls. вход cat /etc/passwd | while read a; do echo "$a"; done –  Matt 11.01.2014, 18:15

ls не требует отдельного процесса. Очень немного команд на самом деле требуют отдельного процесса: только те, которые должны изменить полномочия.

Как правило, оболочки реализуют команды как builtins только, когда те команды должны быть реализованы как builtins. Команды как alias, cd, exit, export, jobs, … должен считать или изменить некоторое внутреннее состояние оболочки и поэтому не может быть отдельными программами. Команды, которые не имеют таких требований, могут быть отдельными командами; этим путем их можно назвать от любой оболочки или другой программы.

При рассмотрении списка builtins в ударе только следующий builtins мог быть реализован как отдельные команды. Для некоторых из них была бы небольшая потеря функциональности.

  • command — но это потеряло бы свою полноценность в ситуациях где PATH может не быть настроен правильно, и сценарий использует command как часть установки его.
  • echo — это - встроенное для эффективности.
  • help — это могло использовать отдельную базу данных, но встраивание текста справки в исполняемом файле оболочки имеет преимущество создания автономного исполняемого файла оболочки.
  • kill — существует два преимущества в наличии встроенного: это может распознать, что обозначения задания, кроме того, обрабатывают идентификаторы, и это может использоваться, даже когда существует недостаточно ресурсов для запуска отдельного процесса.
  • printf — по той же причине как echo, и также поддерживать -v опция поместить вывод в переменную.
  • pwd — встроенные предложения дополнительная возможность логического отслеживания текущего каталога (оставляющий символьные ссылки, неповрежденные вместо того, чтобы развернуть их).
  • test — это - встроенное для эффективности (и удар также делает некоторое волшебство с названными файлами /dev/fd/… в некоторых операционных системах).

Несколько оболочек предлагают значительное количество дополнительного builtins. Существует пояс, который является оболочкой, разработанной, чтобы быть автономным двоичным файлом для срочных ремонтов (когда некоторые внешние команды не могут быть применимыми). Это имеет встроенное ls, названный -ls, а также другие инструменты такой как -grep и -tar. builtins пояса имеют меньше возможностей, чем законченные команды. Zsh предлагает некоторый подобный builtins в своем zsh/files модуле. Это не имеет ls, но подстановочное расширение (echo *) и zstat может выполнить подобную функцию.

2
27.01.2020, 19:50

Я думаю, что что-то, что люди пропускают здесь, является сложностью сдвига GNU ls программа на Linux. Сравнение исполняемого размера ls к bash и dash оболочки в моей системе Debian, мы видим, что это является довольно большим:

graeme@graeme:~$ ls -lh /bin/{ls,bash,dash}
-rwxr-xr-x 1 root root 953K Mar 30  2013 /bin/bash
-rwxr-xr-x 1 root root 115K Dec 25 20:25 /bin/dash
-rwxr-xr-x 1 root root 108K Jul 20 22:52 /bin/ls

Включая ls столь же полнофункциональный как версия GNU в bash увеличил бы исполняемый размер на 10%. Это - почти тот же размер как полное dash оболочка!

Большая часть оболочки builtins выбрана, потому что они интегрируются с оболочкой способом, что внешние исполняемые файлы не могут (вопрос указать cd, но другим примером является версия удара kill интеграция с управлением заданиями удара) или потому что они - очень простые команды для реализации, давая большую скорость по сравнению с выплатой размера (true и false почти так просты, как это добирается).

GNU ls имел долгий цикл разработки, и реализации могут опции настроить, какие результаты отображены. Используя встроенный ls по умолчанию или потерял бы эту функциональность или значительно увеличил бы сложность оболочки и размер.

2
27.01.2020, 19:50

cd встроен в оболочку, ls отдельная программа, в которой Вы будете видеть /bin/ls.

1
27.01.2020, 19:50

Это делает то, что Вы ищете:

printf "%s\n" *

Также можно сохранить имена файлов в массиве:

files=(`printf "%s\n" *`)  #items are separated by whitespace
echo ${#files[*]} files
for index in ${!a[*]}
do printf "%d: %s\n" $index ${a[$index]};
done

Но это не заботится о пробелах на имена
Это передает переменной, и сделайте заботы о пробелах:

printf "%s\n" * | while read a; do echo $a; done
0
27.01.2020, 19:50

Теги

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