В чем разница между / tmp и / run?

42

Согласно FHS-3.0 , /tmpдля временных файлов и /runдля переменных данных во время выполнения. Данные в /runдолжны быть удалены при следующей загрузке, что не требуется /tmp, но программы не должны предполагать, что данные /tmpбудут доступны при следующем запуске программы. Все это похоже на меня.

Итак, в чем разница между этими двумя? По какому критерию программа должна решить, помещать /tmpили вводить временные данные /run?

Согласно FHS:

Программы могут иметь подкаталог /run; это рекомендуется для программ, которые используют более одного файла времени выполнения.

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

Хотя нижеприведенное обоснование не приводится в FHS, оно /runбыло введено для преодоления проблемы, которая /varбыла установлена ​​слишком поздно, так что для того, чтобы сделать ее /var/runдоступной достаточно рано, потребовались грязные приемы . Тем не менее, сейчас, когда /runего представили и дали описание в FHS, нет четкой причины иметь и то, /runи другое /tmp.

Дирк Херрманн
источник
11
/ tmp - это стандартное расположение * nix для временных данных. / run - стандартное расположение Poettering для временных данных.
Марк
Обратная совместимость всегда является причиной ...
Бакуриу

Ответы:

16

Нет причин иметь оба / run и / tmp

Я думаю ты прав. /tmpпо сути устарел сейчас у нас /run. Если ваша программа в состоянии сделать это (что требует, чтобы она была установлена как привилегированная операция), то в настоящее время вы должны использовать подкаталог /run. Это из соображений безопасности.

Например, демон печати CUPS не запускается от имени пользователя root, но обычно устанавливается из пакета ОС. Пакет устанавливается /usr/lib/tmpfiles.d/cups.confи systemd-tmpfilesсоздает каталог, к которому он может получить доступ. Поскольку каталог находится в папке /run, непривилегированное пользователь не может получить злонамеренное имя, в отличие от того, /tmpкоторое доступно для записи всем пользователям.

«Непривилегированные программы», которые нельзя использовать /runнапрямую

Настоящее различие заключается в том, что ваша программа запускается произвольным непривилегированным пользователем под своим собственным идентификатором пользователя. Но вы все равно, как правило, не хотите использовать /tmp, потому что к нему могут получить доступ другие непривилегированные пользователи. Вы бы предпочли использовать $XDG_RUNTIME_DIR. Как правило, это реализуется как /run/user/$(id -u)- так что это, оказывается, также подкаталог /run. Расположение не гарантируется, хотя; программы всегда должны использовать переменную окружения.

/tmpбудет полезно только для специального сотрудничества между различными непривилегированными пользователями в системе. Такие специальные системы уязвимы для злонамеренного пользователя, отказывающегося сотрудничать и портящего вещи для всех :). Одним из примеров могут быть непривилегированные пользователи, решившие запустить версию talkдемона, используя сокет unix.

Оригинальная информация от Lennart Poettering

Обратите внимание, что в приведенном ниже контрольном списке Poettering указано, что /tmpэто будет полезно для «маленьких файлов», тогда как /runследует использовать только для «коммуникационных примитивов». Я не думаю, что это различие также верно. Автор плаката для /runis udev, и я уверен, что /run/udevвключает в себя внутренние базы данных. Если у вас есть /runкаталог, я не думаю, что кто-то захочет следовать заявленному различию и создать еще один каталог, чтобы загромождать /tmp. Так что на практике мы просто используем в /runнаше время.

Использование общедоступных общих пространств имен [like / tmp] для целей связи всегда было проблематичным, поскольку для установления связи нужны стабильные имена, но стабильные имена открывают двери для DoS-атак. Это может быть исправлено частично путем создания защищенных каталогов для приложений для определенных сервисов во время ранней загрузки (как мы делаем для X11), но это только частично устраняет проблему, поскольку это работает правильно, только если после каждой установки пакета происходит перезагрузка.

...

Другая функция Fedora (для Fedora 17) изменила семантику / tmp для многих системных сервисов, сделав их более безопасными, изолировав пространства имен / tmp различных сервисов

...

Поскольку / tmp больше не обязательно является общим пространством имен, он обычно не подходит в качестве места для примитивов связи.

...

[/ run] гарантированно будет tmpfs и, следовательно, автоматически сбрасывается при загрузке. Никакой автоматической очистки не производится.

...

Вот примерное руководство о том, как мы предлагаем вам (разработчику приложений для Linux) выбрать правильный каталог для использования:

  1. Вам нужно место для размещения вашего сокета (или другого коммуникационного примитива), и ваш код запускается с привилегиями: используйте подкаталог ниже / run. (Или под / var / run для дополнительной совместимости.)
  2. Вам нужно место для размещения вашего сокета (или другого коммуникационного примитива), и ваш код выполняется непривилегированным: используйте подкаталог под $ XDG_RUNTIME_DIR.
  3. Вам нужно место, где вы можете загружать и загружать большие файлы и запускать их без привилегий: используйте $ XDG_DOWNLOAD_DIR.
  4. Вам нужно место для размещения файлов кэша, которые должны быть постоянными и работать непривилегированно: используйте $ XDG_CACHE_HOME.
  5. Ничто из вышеперечисленного не применимо, и вам нужно поместить небольшой файл, который не нуждается в постоянстве: используйте $ TMPDIR с резервным вариантом на / tmp. И используйте mkstemp (), и mkdtemp () и ничего доморощенного.
  6. В противном случае используйте $ TMPDIR с откатом на / var / tmp. Также используйте mkstemp () / mkdtemp ().

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

Одна вещь, которую мы хотели бы подчеркнуть, это то, что / tmp и / var / tmp чаще всего не являются правильным выбором для вашего варианта использования. Существуют допустимые варианты использования этих каталогов, но нередко лучше использовать другой каталог. Поэтому будьте осторожны, рассмотрите другие варианты, но если вы все же выберете / tmp или / var / tmp, то, по крайней мере, обязательно используйте mkstemp () / mkdtemp ().

Мы отошли от устаревшего /tmpсокета, используемого системой X Window, как описано выше. Я неправильно понял tmpfiles.d/x11.conf. Похоже, что это зависит от сотрудничества :). Я предполагаю, что код был проверен, так что отказ в обслуживании - худшее, что может произойти.

sourcejedi
источник
8
Этот ответ неверен.
R ..
@R .., хочешь рассказать об этом?
Wildcard
Да, я уже сделал в ответ. (Начал как комментарий, но я понял, что это был скорее ответ.)
R ..
Я думаю, что основной недостаток моего текущего ответа, над которым, я думаю, вы работали, заключается в том, что хотя технически правильная обработка XDG_RUNTIME_DIR должна быть переносимой на любой * nix («возврат к каталогу замены с аналогичными возможностями»), это очень расплывчато, что это означает на практике. Для переносимых утилит лучше использовать четко определенный стандарт для /tmp(«единственными API для его использования должны быть mkstemp (), mkdtemp () (и друзья) для полной безопасности»).
sourcejedi
Ответ отсутствует и в общем случае: /var/runэто общесистемная система (например, для связи с локальной базой данных), /tmp/теперь она часто создается для каждого пользователя . Исторически также квота / tmp была установлена ​​иначе. И ответ пропускает, что семантическое различие использования также важно.
Джакомо Катенацци
23

Каталоги /tmpи /usr/tmp(позже /var/tmp) раньше были свалкой для всего и всех. Единственным механизмом защиты файлов в этих каталогах является залипающий бит, который ограничивает удаление или переименование файлов там их владельцам. Как отметил Марсельм в комментарии, в принципе нет ничего, что мешало бы кому-либо создавать файлы с именами, которые используются службами (такими как nginx.pidили sshd.pid). (На практике сценарии запуска могут сначала удалить такие поддельные файлы.)

/runбыл создан для непостоянных данных времени выполнения долгоживущих сервисов, таких как блокировки, сокеты, pid-файлы и тому подобное. Так как он недоступен для записи для общественности, он защищает данные времени выполнения службы от беспорядка /tmpи заданий, которые там очищаются. В самом деле: Два дистрибутива, которые я запускаю (без каламбура), имеют разрешения 755 /run, в то время как /tmpи /var/tmp/dev/shmв этом отношении) имеют разрешения 1777.

countermode
источник
3
это просто для того, чтобы отделить данные времени выполнения сервиса от беспорядка/tmp - Также, чтобы обеспечить безопасную гавань для упомянутых данных от различных заданий по очистке, которые растоптаны повсюду /tmp.
Satō Katsura
Спасибо за информацию о разрешениях. Однако, согласно FHS, «Программы могут иметь подкаталог / run; это рекомендуется для программ, которые используют более одного файла времени выполнения». - это, кажется, противоречит как критерию «долгоживущих сервисов», так и неспособности программ создавать свои подкаталоги из-за ограниченных разрешений.
Дирк Херрманн
@DirkHerrmann Нет, это не так. Посмотрите /runи проверить сложные (хорошо ...) структуру каталогов , вызванных udev, и udiskт.д. Я не являюсь экспертом по этому конкретному вопросу, но я предполагаю , что загрузочные скрипты (которые работают в качестве суперпользователя) установить все.
контррежим
2
«/ run технически необязателен, он просто служит для отделения данных времени выполнения службы от беспорядка в / tmp». - Это тоже хорошо, поэтому непривилегированные процессы не могут присваивать имена системным службам, которые хотят использовать. Kinda отстой, если nginx хочет его использовать, /tmp/nginx.pidно он уже существует из-за неправильной работы программы. /run/предотвращает это, требуя привилегий для записи.
Марселм
18

/tmpэто место для создания временных файлов и каталогов. Он не пригоден для хранения «общеизвестных имен» (т. Е. Имен, о которых может знать другой процесс без необходимости каким-либо образом передавать ему имя), потому что никто не владеет пространством имен; каждый может создавать файлы там. Как таковой, вы обычно используете его, когда у вас есть утилита, которой нужен файл (т.е. не труба или что-то подобное) в качестве ввода или вывода, где любое (случайно сгенерированное) имя будет работать, пока вы передаете имя.

Исторически, некоторые вещи (например, X) нарушали этот принцип и помещали известные имена (например .X11-unix) в /tmp. Это, конечно, глючит и позволяет любому пользователю делать DoS сервис, которому это нужно, просто гоняя, чтобы сначала создать файл с нужным именем. Такие вещи принадлежат /run(или эквивалентно, /var/runесли вы не подписаны на ревизионизм Freedesktop.org). Конечно, еще лучше было бы исправить их, чтобы они не использовали известные имена в глобальном пространстве имен, а вместо этого передавали путь.

Р..
источник
Спасибо за еще одно определение "временных файлов". Хотя я не думаю, что «обойти путь» объясняет, как установить точку координации. Т.е. обычно вы бы использовали переменную окружения. Похоже, там достаточно нескольких розеток и трубок (для общего пользования), чтобы это работало. (Отчасти потому, что многие вещи будут работать через один и тот же сокет dbus). Похоже, было бы неприятно устанавливать среду, если программы по умолчанию не указывали жестко заданный путь. Вы можете добавить новый ключ в системные .socketфайлы ... но это не поможет ни для целых каталогов, ни для вновь установленных служб
sourcejedi
2
/run/Сам по себе был принят FHS, я не вижу, как это имеет отношение к fd.o. Если на самом деле мы не хотели жаловаться, то это неопределенные усилия по развитию, которые способствовали обоим.
sourcejedi
Я думаю, что первоначальный ответ здесь является лучшим ответом на этот вопрос в том виде, в котором он написан Я думаю, что это будет улучшено, если учесть: _Если программное обеспечение имеет доступ на запись в выделенный каталог, например /run, в него, оно может предпочесть избежать загромождения общего /tmpкаталога еще большим количеством файлов.
sourcejedi
Что такое "fd.o"?
TRiG
7

Согласно стандарту иерархии файловой системы,

  • /run для переменных данных времени выполнения, т.е. информации о работающей системе с момента перезагрузки
  • /tmp это общее место для временных файлов.

Таким образом, все, что касается статуса демона, зарегистрированных пользователей, подключенных съемных устройств и т. Д., Будет входить в /runто время, когда будут создаваться временные файлы, созданные программой /tmp.

Изменить: как указано @JdeBP в комментарии ниже,

FHS допускает такие вещи, как обычная настройка заданий cron, которые регулярно удаляют /tmp«старые» файлы; без таких механизмов, предназначенных для /run. Отсюда и драконовский предел того, что программы могут ожидать от срока службы чего-либо введенного /tmp. В то время как программы могут ожидать, что файлы будут жить дольше в /runпостоянно работающей системе, они также должны привести себя в порядок.

dr01
источник
4
Одна вещь, не указанная в этом или любом другом ответе, но отмеченная в FHS, и с которой вы могли бы улучшить свой ответ: FHS допускает такие вещи, как обычная настройка заданий cron, которые регулярно удаляют /tmp«старые» файлы; без таких механизмов, предназначенных для /run. Отсюда и драконовский предел того, что программы могут ожидать от срока службы чего-либо введенного /tmp. В то время как программы могут ожидать, что файлы будут жить дольше в /runпостоянно работающей системе, они также должны привести себя в порядок.
JdeBP
1
Было бы неплохо иметь для каждого процесса каталог с вещами, которые исчезли (или были допущены к удалению каким-либо перемещаемым демоном мусора), как только процесс завершился.
всевозможный
1
@ Omnifarious, теперь вы можете получить такое поведение для службы systemd, используя RuntimeDirectory = :-).
Sourcejedi