Я работаю над проектом, который реализует распределенное моделирование: произвольный код выполняется на нескольких узлах, а затем результаты собираются и объединяются.
Каждый узел является экземпляром виртуальной машины Ubuntu Linux и запускает главный процесс, который заботится о пересылке кода, который должен быть выполнен, ряду рабочих процессов (по 1 для каждого ядра).
Этот вопрос о том, как убедиться, что каждый работник работает в изолированной среде, не прибегая к использованию экземпляра виртуальной машины для каждого из них. Точные требования к работникам:
- fs : нет разрешения на запись, разрешение только на чтение ограничено одним каталогом (и подпапками)
- net : разрешены только локальные коммуникации (IPC, TCP, что угодно ...)
- mem : ограничение использования памяти (без подкачки памяти). kill, если превышен предел памяти.
- процессор : разрешено только 1 ядро, убить если ограничение по времени
Не должно быть никаких других ограничений: рабочий должен иметь возможность загружать динамические библиотеки (из папки только для чтения), порождать новые потоки или процессы, вызывать системную функцию, ecc ecc, но ограничения должны наследоваться порожденными / загруженными объектами и следует применять суммированным образом (например, у нас не может быть рабочего, порождающего два потока, каждый из которых использует 800 МБ, поскольку ограничение памяти для такого рабочего составляет 1 ГБ).
Само собой разумеется, что у работника не должно быть возможности повысить свои права.
Я потратил немало времени на рассмотрение доступных альтернатив (SELinux, AppArmor, cgroups, ulimit, пространства имен Linux, LXC, Docker, ...) для самого простого решения, которое удовлетворяет моим требованиям, но мой опыт работы в этой области ограничен.
Текущее понимание: LXC и Docker немного сложны для моего случая использования и не полностью безопасны 1 . AppArmor предпочтительнее SELinux из-за более простой настройки, используйте его для ограничений fs и net; cgroups предпочтительнее ulimit (который работает на одном процессе), использует его для ограничений mem и cpu.
Это самый простой способ достичь моей цели? Могу ли я использовать AppArmor или cgroups исключительно? Есть ли в моей модели очевидная дыра в безопасности? Руководящий принцип должен быть «работнику разрешено самоуничтожиться, но не более того» .