Создание временного файла по сравнению с заменой процесса по сравнению с переменным расширением?

man ntfs-3g говорит:

Если ntfs-3g будет установлен setuid-корень затем, то некорневые пользователи также смогут смонтировать объемы.

ls -ld $(which ntfs-3g) говорит, что мой испытывает недостаток в setuid. Ваш?

4
23.01.2017, 20:25
2 ответа

Замена процесса Bash в форме <(cmd) и >(cmd) реализован с именованными каналами, если система поддерживает их. Команда cmd выполняется с его вводом/выводом, подключенным к каналу. Когда Вы работаете, например. cat <(sleep 10; ls) можно найти созданный канал в соответствии с каталогом /proc/pid_of_cat/fd. Этот именованный канал затем передается как аргумент текущей команде (cat).

Буферная емкость канала может быть оценена с хитрым использованием dd команда, которая отправляет нулевые данные в стандартный вход sleep команда (который ничего не делает). По-видимому, процесс будет спать некоторое время, таким образом, буфер станет полным:

(dd if=/dev/zero bs=1 | sleep 999) &

Дайте ему секунду и затем отправьте USR1 предупредите к dd процесс:

pkill -USR1 dd

Это делает процесс для распечатывания статистики ввода-вывода:

65537+0 records in
65536+0 records out
65536 bytes (66 kB) copied, 8.62622 s, 7.6 kB/s

В моем тестовом сценарии размер буфера 64kB (65536B).

Как Вы используете <<<(cmd) расширение? Я знаю, это - изменение здесь документов, которое расширено и передано команде на ее стандартном входе.

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

5
27.01.2020, 20:48
  • 1
    Хорошая рецензия. OP, вероятно, предназначен <<<"$(...)" вместо <<<(...). Вот автоматизированная острота, которая работает над Linux и BSD/macOS для измерения размера буфера канала (выходные результаты после 2 secs.): dd if=/dev/zero bs=1 | sleep 999 & sleep 2 && pkill -INT -P $$ -x dd –  mklement0 23.01.2017, 20:44

<(cmd) a ksh функция, также найденная в наше время в zsh и bash названная замена процесса.

В системах та поддержка /dev/fd/n или /proc/self/fd/n, это реализовано с каналами и если не с временными именованными каналами. В любом случае это - форма канала, который является механизмом межпроцессорного взаимодействия.

cmd1 <(cmd2)

Может быть записан (с нормальными каналами):

{ cmd2 4<&- | 3<&0 <&4 4<&- cmd1 /dev/fd/3; } 4<&0

Или (с именованными каналами):

mkfifo /tmp/named_pipe
cmd2 > /tmp/named_pipe & cmd1 /tmp/named_pipe

Таким образом, обе команды запускаются одновременно и общаются с каналом. Вы обычно использовали бы cmd2 | cmd1 для этого, но замены процесса обычно для тех случаев где cmd1 может только взять вход от имени файла а не от стандартного входа или когда больше чем один вход необходим как в diff <(cmd1) <(cmd2).

Нет никакого rlimit влияния на него кроме общих как на количестве процессов, процессорное время или память.

PIPEBUF, о котором сообщают некоторые реализации ulimit как bash и некоторые реализации ksh не rlimit, но максимальный размер, для которого запись к каналу, как гарантируют, будет атомарной, так не важно здесь. Размер самого канала (64 КБ на Linux, как сообщается @dsmsk80) не является действительно самим пределом. Это просто говорит, что это так же cmd2 может записать в канал даже после cmd1 прекратил читать из него.

Существует ограничение хотя в этом cmd1 может только читать из того файла. Поскольку это - канал, это не может записать в тот файл или искать назад и вперед в файле.

zsh имеет третью форму замены команды с помощью регулярных временных файлов:

cmd1 =(cmd2)

вызовы cmd1 с временным файлом, который содержит вывод cmd2. В этом случае cmd1 бежится cmd2 вместо одновременно. Предел на размер файлов может быть достигнут там.

Я не знаю ни о какой оболочке, реализовывая a <<<(...) оператор. Существует однако a <<< оператор в zsh (вдохновленный тем же оператором в порте Unix rc) также найденный в последних версиях ksh93 и bash. Это - вариация на << оператор heredoc, названный herestring.

В:

cmd <<< something

Который совпадает со стандартом:

cmd << EOF
something
EOF

Оболочка создает временный файл с something\n как содержание и подача, что, поскольку стандартный вход к новому процессу, удаляет связь с тем файлом и выполняется cmd в том новом процессе. Снова, это - регулярный файл, таким образом, rlimit на максимальном размере файла может быть достигнут.

Теперь можно объединиться <<< оператор с $(...) (управляйте заменой) так или иначе эмулировать zsh =(...) оператор в bash и ksh93:

cmd1 <<<"$(cmd2)"

Работал бы cmd2 с ним stdout, перенаправленный к каналу. На другом конце канала оболочка читает вывод cmd2 и хранилища это минус запаздывающие символы новой строки и с одним символом новой строки, добавленным во временный файл и вызов cmd1 с тем временным файлом, открытым для чтения как stdin (примечание существует другое ограничение, в котором это не будет работать если cmd2 вывод содержит символы NUL).

Быть похожими =(...), необходимо было бы записать это:

cmd1 /dev/fd/3 3<<<"$(cmd3)"

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

Также обратите внимание что начиная с версии 5, bash разделяет полномочия записи во временный файл перед вызовом cmd1, таким образом, если Вам нужно cmd1 чтобы смочь изменить тот файл, необходимо было бы работать вокруг этого с:

{
  chmod u+w /dev/fd/3 && # only needed in bash 5+
  cmd1 /dev/fd/3
} 3<<<"$(cmd3)"
5
27.01.2020, 20:48
  • 1
    Но это, кажется, не работает: ssh -F /dev/fd/3 default 3<<<"$(vagrant ssh-config)" –  Sukima 10.11.2017, 03:31
  • 2
    @Sukima, посмотрите, Почему не делает замены процесса <(), работа с ssh-F. ssh закрывает весь свой fds кроме 0, 1, 2 на запуске. –  Stéphane Chazelas 10.11.2017, 15:00
  • 3
    Хорошо это разбивает и нарушает. Я желаю программ Unix, все действовали как вздох программ Unix. Спасибо за статью. Я закончил тем, что имел необходимость сделать эти четыре строки в файле сценария: conf=“$(mktemp -t fix_moron_ssh)”; vagrant ssh-config >”$conf”; trap ‘rm -f “$conf”’ EXIT; exec ssh -F “$conf” default “$@“. –  Sukima 10.11.2017, 15:22
  • 4
    @Sukima, ssh делает это потому что (заключающий в кавычки из кода): "Отбросьте другие fds, которые бродят вокруг. Они могут вызвать проблему с фоном ssh процессы, запущенные ControlPersist". Я согласился бы, что было бы более хорошо, если бы это только сделало это для процесса, бродящего вокруг для сохранения основного соединения. Существуют другие команды как sudo где это имеет большой смысл закрыть весь fds. –  Stéphane Chazelas 10.11.2017, 15:45

Теги

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