FUSE в rootless, непривилегированном podman

Вопрос или проблема

Вопрос

Добавление CAP_SYS_ADMIN все еще единственный способ работать с fuse внутри контейнера без root-прав (как с нативным overlay, так и с fuse-overlayfs/другими методами)?


Примеры

Podman в podman

Этот пример из https://www.redhat.com/en/blog/podman-inside-container

podman run --user podman --security-opt label=disable --device /dev/fuse -ti quay.io/podman/stable podman run -ti docker.io/busybox echo hello

работает у меня без проблем. Но это дает мне повод предполагать, что использован fusermount внутри контейнера или что его можно использовать, что не работает при использовании той же настройки.

Более того, похоже, что ничего не монтируется:

podman run --user podman --security-opt label=disable --device /dev/fuse -ti quay.io/podman/stable
# выполнение команд в контейнере
cat /proc/mounts > /home/podman/before
podman run -d docker.io/busybox sleep 100
cat /proc/mounts > /home/podman/during
diff /home/podman/before /home/podman/during
# (нет различий)

Кажется, что и без /dev/fuse также работает (тестировалось с нативным overlay):

podman run --user podman --security-opt label=disable -ti quay.io/podman/stable podman run -ti docker.io/busybox echo hello

Bindfs

Просто добавьте bindfs в образ

FROM quay.io/podman/stable

RUN dnf -y install bindfs

И запуск контейнера

podman run --user podman --security-opt label=disable --device /dev/fuse -ti built_image_from_above:latest
# внутри контейнера
cd ~ && mkdir test1 test2
bindfs --no-allow-other test1 test2
fusermount: mount failed: Operation not permitted

Я предполагаю, что поведение будет таким же для других fuse монтирований, таких как sshfs.
Может ли это быть проблемой разрешений внутри контейнера или это отрицается на хосте?


Идеи

нужны привилегии

Этот ответ подразумевает, что для использования fuse нужны привилегии.

Упоминается Setuid, но я не уверен, как это предполагалось.
Внутри контейнера:

ls -l $(which fusermount3)
-rwsr-xr-x. 1 root root 40800 Jul 17 00:00 /usr/bin/fusermount3

rootless overlay

Я также попытался удалить строку mount_program из storage.conf и выполнить podman system reset, как описано здесь. Но я не уверен, касается ли это только overlay или также fuse. Если я не добавлю /dev/fuse, устройство отсутствует в контейнере:

Еще один недостаток fuse-overlayfs заключается в том, что он требует доступа к
/dev/fuse. Когда люди пытаются запустить Podman и Buildah в ограниченном
контейнере, мы отнимаем привилегии CAP_SYS_ADMIN, даже когда
работаем как root. Это заставляет нас использовать пространство имен пользователя, чтобы мы могли
монтировать тома. Чтобы это работало, пользователи должны добавить /dev/fuse
в контейнер. Как только у нас появится нативный overlay для режима без root (без
CAP_SYS_ADMIN), /dev/fuse больше не будет требоваться.


Версии

Host: Fedora 41
Podman: 5.3.1

Похоже, я нашел решение (сделал пример как можно короче):

podman run --device /dev/fuse -ti fedora:41
# внутри контейнера
cd ~ && mkdir test1 test2
unshare -pfr --user --mount --kill-child /bin/bash
# теперь внутри процесса в новом ns
bindfs --no-allow-other test1 test2
# монтирование прошло успешно

Источник: https://zameermanji.com/blog/2022/8/5/using-fuse-without-root-on-linux/#alternative-approach

Это была проблема возможностей, потому что, при тестировании, это работало с любым из флагов:

  • --privileged (отключает большинство механизмов безопасности)
  • --cap-add=all (только отключает сброс капов)

Похоже, что непривилегированные монтирования fuse возможны, когда они выполняются из нового пространства имен пользователя и монтирования. Я не уверен, может ли podman подготовить пространства имен – он может манипулировать пространствами имен пользователя, но я не нашел ничего о пространстве имен монтирования.
Но выполнение unshare -pfr --user --mount --kill-child /bin/bash в контейнере, похоже, работает нормально.

Флаг --security-opt label=disable также не кажется обязательным.

.

Ответ или решение

Использование технологий FUSE (Filesystem in Userspace) без привилегий в контейнере Podman стало важным аспектом для многих разработчиков. Вопрос о том, как воспользоваться FUSE внутри rootless контейнера без добавления CAP_SYS_ADMIN, неизменно возбуждает интерес.

Проблематика и контекст

Традиционно для монтирования FUSE в контейнере необходимы права администратора системы (CAP_SYS_ADMIN). Однако, повышенные привилегии вносят дополнительные риски безопасности, что неприемлемо в большинстве сценариев использования. Рассматриваемый пример демонстрирует использование Podman в контейнере и поднимает вопросы о возможности использования fusermount без явного монтирования.

Решение

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

Шаги для реализации:

  1. Создание контейнера с доступом к /dev/fuse:
    podman run --device /dev/fuse -ti fedora:41
  2. Создание директорий для монтирования внутри контейнера:
    cd ~ && mkdir test1 test2
  3. Запуск оболочки в изолированном пространстве:
    unshare -pfr --user --mount --kill-child /bin/bash
  4. Выполнение команды монтирования:
    bindfs --no-allow-other test1 test2

Оптимизация и заключение

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

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

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

Оцените материал
Добавить комментарий

Капча загружается...