Bug 16706

Summary: [FR] Сборка на tmpfs
Product: Sisyphus Reporter: Mikhail Gusarov <dottedmag>
Component: hasherAssignee: Dmitry V. Levin <ldv>
Status: NEW --- QA Contact: qa-sisyphus
Severity: enhancement    
Priority: P2 CC: at, erthad, evg, glebfm, kas, ldv, legion, mike, placeholder, vvk
Version: unstable   
Hardware: all   
OS: Linux   
Attachments:
Description Flags
Первая реализация none

Description Mikhail Gusarov 2008-08-15 23:18:20 MSD
Хочется увидеть в самом hasher возможность сборки пакетов на tmpfs, дабы не приходилось пользоваться кустарными методами, типа описанного в http://www.altlinux.org/TmpFS
Comment 1 Mikhail Gusarov 2008-08-16 01:22:15 MSD
Created attachment 2787 [details]
Первая реализация

Реализация сборки на tmpfs в виде враппера вокруг hsh. Вместо workdir принимает repodir (как непосредственно видимую пользователю).
Comment 2 Alexey Gladkov 2008-08-17 13:46:19 MSD
Я не понял назначение этого скрипта. Мне не понятно почему сложно выполнить команду из exec руками. Например так, если у вас /tmp на tmpfs:

hsh --repo=~/tmp $TMPDIR <SRPM>

Этот скрипт безусловно не реализация сборки на tmpfs т.к. в скрипте tmpfs не упоминается вообще. Скрипт только генерирует WORKDIR самостоятельно в /tmp/.private, а он не обязательно должен быть на tmpfs.

Зачем используется gear-sh-functions ?

Это пользовательский скрипт и он должен замаскировать работу с WORKDIR, но вы не проверяете можно ли собирать /tmp/.private. Так и задумано?

После выполнения скрипта в /tmp/.private/$USER/ будут копиться WORKDIR от разных репозитриев. Если предположить что /tmp/.private на tmpfs, то такой подход будет просто замусоривать память.

Пользователю будет не очевидно, что потом ему нужно идти в /tmp/.private/$USER/, искать созданный каталог и чистить его т.к. никаких сообщений о том как называется WORKDIR не выводится.

Пока писал, подумал вот о чём: А зачем выделаете разные WORKDIR для разных репозиториев? hasher всё равно кэширует только базовую часть репозитория. Мне думается, что с учётом того что вы вынесли REPO из WORKDIR, в создании разных WORKDIR нет смысла.
Comment 3 Mikhail Gusarov 2008-08-17 14:09:04 MSD
(In reply to comment #2)

> Я не понял назначение этого скрипта. Мне не понятно почему сложно выполнить
> команду из exec руками.

Несложно. Только на двадцатый-тридцатый-пятидесятый-сотый раз начинает надоедать подпихивать аргументы ручками в два-три разных хэшерницы и тогда садишься писать ровно такой же скрипт. Зачем каждому человеку писать аналогичный скрипт, когда можно положить готовую реализацию, которая покроет 80% (с потолка) потребностей?

> Этот скрипт безусловно не реализация сборки на tmpfs т.к. в скрипте tmpfs не
> упоминается вообще. Скрипт только генерирует WORKDIR самостоятельно в
> /tmp/.private, а он не обязательно должен быть на tmpfs.

Да, это проблема. См. ниже.

> Зачем используется gear-sh-functions ?

По ошибке.

> Это пользовательский скрипт и он должен замаскировать работу с WORKDIR, но вы
> не проверяете можно ли собирать /tmp/.private. Так и задумано?

Ошибка.

> После выполнения скрипта в /tmp/.private/$USER/ будут копиться WORKDIR от
> разных репозитриев. Если предположить что /tmp/.private на tmpfs, то такой
> подход будет просто замусоривать память. Пользователю будет не очевидно, что
> потом ему нужно идти в /tmp/.private/$USER/, искать созданный каталог и
> чистить его т.к. никаких сообщений о том как называется WORKDIR не выводится.

Это вопрос, который стоит обсудить.

Тут я вижу два выхода:

1) Сборка на создаваемом/очищаемом tmpfs - тогда проблемы с мусором не будет, но не будет и возможности воспользовать --lazy-cleanup. Кроме того, в этом случае придётся дополнительно хранить cache рядом или внутри репозитория.

2) Сборка как сейчас (с дополнительной проверкой на то, что workdir располагается на tmpfs) и дополнительная утилита hsh-tmpfs-cleanup. В этом случае весь функционал hasher сохраняется, но появляется дополнительная "ручка", которую нужно периодически дёргать.

> Пока писал, подумал вот о чём: А зачем выделаете разные WORKDIR для разных
> репозиториев? hasher всё равно кэширует только базовую часть репозитория. Мне
> думается, что с учётом того что вы вынесли REPO из WORKDIR, в создании разных
> WORKDIR нет смысла.

А если репозитории разные?
Comment 4 Alexey Gladkov 2008-08-17 14:22:01 MSD
(In reply to comment #3)
> Это вопрос, который стоит обсудить.
> 
> Тут я вижу два выхода:

Есть выход использовать только один WORKDIR. Тогда копиться ничего не будет и cache будет на месте.

Минусы подхода:
1) Нужна дополнительная работа по прописыванию REPO в sources.list в случае, если репозитории разные. Это не сложно.

2) Пользователь должен знать о WORKDIR, чтобы иметь возможность её удалить. И таким образом совсем спрятать WORKDIR не получится... хотя такой задачи и не ставится.

> А если репозитории разные?

см. выше пункт #1.
Comment 5 Mikhail Gusarov 2008-08-17 14:29:32 MSD
(In reply to comment #4)

> Есть выход использовать только один WORKDIR. Тогда копиться ничего не будет и
> cache будет на месте.

А как осуществлять переключение "я хочу собрать этот пакет в среде branch/4.0"? --apt-conf при каждом запуске? Но при использовании hsh очень удобно при создании workdir указать настройки и в дальнейшем просто показывать на нужную директорию. Хочется и с hsh-tmpfs добиться того же результата.

> 2) Пользователь должен знать о WORKDIR, чтобы иметь возможность её удалить. И
> таким образом совсем спрятать WORKDIR не получится... хотя такой задачи и не
> ставится.

С этим согласен - удалять её (или их, если их много) всё равно кому-нибудь придётся.
Comment 6 Alexey Gladkov 2008-08-17 14:56:57 MSD
(In reply to comment #5)
> Хочется и с hsh-tmpfs добиться того же результата.

Но hsh в этом плане проще. Пользователь сам говорит, что он хочет и явно указывает WORKDIR. В случае hsh-tmpfs это сделать намного сложнее. Чтобы добиться такого же эффекта и не идти по экстенсивному пути с множественными WORKDIR, придётся городить своё вспомогательное хранилище, где сохранять sources.list и cache-dir для каждого REPO. А при переключении с одного REPO на другой выполнять --clean на WORKDIR.
Comment 7 Mikhail Gusarov 2008-08-17 15:02:44 MSD
А чем плох экстенсивный путь? Между workdir и repodir сохраняется соответствие 1-1. Если дополнительно утащить cache на диск, внурь repodir, то размер workdir будет совсем небольшим.
Comment 8 Kirill A. Shutemov 2008-08-17 15:04:55 MSD
Я поступил проще.
У меня в fstab есть строчка:
tmpfs           /home/kas/hasher        tmpfs   size=4G                      0 0
Мне хватает.
Comment 9 Mikhail Gusarov 2008-08-17 15:19:42 MSD
Для одной машины и для одного хашера я и сам руками в fstab чего-нибудь напишу. Вопрос совершенно не в этом.
Comment 10 Alexey Gladkov 2008-08-17 18:29:57 MSD
(In reply to comment #7)
> А чем плох экстенсивный путь? Между workdir и repodir сохраняется
> соответствие 1-1.

Тем что он экстенсивный :)

Я понимаю, вы хотите держать по одному REPO на каждый бранч. Но ведь есть люди, которые делают отдельный REPO на пакет (или зависимую группу пакетов). Это не противоречит идее hasher. И в этом случае WORKDIR'ов у пользователя будет больше. 

> Если дополнительно утащить cache на диск, внурь repodir

Как раз cache стабилен по размеру и меняется не часто и не сильно. Ведь это базовая часть *любого* чрута для сборки. Если из WORKDIR убрать cache, repo и aptbox (как я фактически предлагаю), то в WORKDIR останется лишь одна директория, которая пересоздаётся для каждой сборки: chroot.

Именно (aptbox + cache) соотносится с repo 1-1.

> то размер workdir будет совсем небольшим.

"Небольшой WORKDIR" понятие относительное. WORKDIR после ash действительно мал относительно WORKDIR после openoffice.org (или mozilla.org). Просто вам везло с проектами (вот мне не везёт), но это не значит что нет больших проектов и то что их мантейнеры не захотят пользоваться вашей утилитой.
Comment 11 Mikhail Gusarov 2008-08-17 18:57:16 MSD
Понял идею. Тогда и правда наиболее удобным будет хранить всё, кроме chroot, в районе repo (точнее, сделать свой "workdir", в котором хранится всё, кроме chroot), и использовать один workdir, в котором только chroot, для всех сборок. 

Правда, вылезет бяка с --number, но и её можно обойти.

Попробую сделать так.
Comment 12 Dmitry V. Levin 2008-08-29 20:29:56 MSD
Есть идея монтировать chroot на отдельный tmpfs во время сборки.  Именно этот каталог используется наиболее интенсивно, он самый большой по размеру и числу файлов.  По сравнению с обычной сборкой на tmpfs, cleanup после сборки таких пакетов как subversion существенно ускорится.  Есть только одна проблема с этим подходом: как такое реализовать относительно безопасным для системы образом.
Comment 13 Alexey Gladkov 2008-08-29 20:50:27 MSD
(In reply to comment #12)
> подходом: как такое реализовать относительно безопасным для системы
> образом.

А в чём проблема?

У нас есть превилегированный хэлпер. Добавить в него ещё одну команду монтирования/размонтирования tmpfs.
Comment 14 Dmitry V. Levin 2008-08-29 20:53:52 MSD
(In reply to comment #13)
> (In reply to comment #12)
> > подходом: как такое реализовать относительно безопасным для системы
> > образом.
> 
> А в чём проблема?
> 
> У нас есть превилегированный хэлпер. Добавить в него ещё одну команду
> монтирования/размонтирования tmpfs.

Непонятно, как это сделать безопасным для хост-системы.
Чтобы обычный пользователь по ошибке не разбудил OOM killer.
Comment 15 Mikhail Gusarov 2008-08-29 20:56:16 MSD
Ввести лимит на максимальный суммарный размер tmpfs'ов, таким образом доступных пользователю?
Comment 16 Alexey Gladkov 2008-08-29 21:02:24 MSD
(In reply to comment #14)
> Чтобы обычный пользователь по ошибке не разбудил OOM killer.

Мне кажется, что от этого мы не сможем застраховаться т.к. мы заранее не знаем какой будет размер чрута.

Кстати, вот ещё одна проблема: как узнать параметры tmpfs чтобы его хватило на чрут? Мы заранее не знаем сколько файлов будет создано и их размер.
Comment 17 Mikhail Gusarov 2008-08-29 21:05:05 MSD
(In reply to comment #16)

> > Чтобы обычный пользователь по ошибке не разбудил OOM killer.
> Мне кажется, что от этого мы не сможем застраховаться т.к. мы заранее не
> знаем какой будет размер чрута.

tmpfs нужного размера всегда можно выделить. Тогда не хост упадёт, а сборка сломается.

> Кстати, вот ещё одна проблема: как узнать параметры tmpfs чтобы его хватило на
> чрут? Мы заранее не знаем сколько файлов будет создано и их размер.

Выставить ручку для регулирования в hsh. Если запрошено больше лимита - отлуплять, если нет ручки - выдать столько, сколько в лимите написано.
Comment 18 Alexey Gladkov 2008-08-29 21:16:17 MSD
(In reply to comment #17)
> tmpfs нужного размера всегда можно выделить. Тогда не хост упадёт, а сборка
> сломается.

Если я правильно понял Диму, то речь шла о автоматическом создании tmpfs и расположении там chroot. В этом случае размер tmpfs и количество inodes предётся считать автоматически иначе в этом нет мысла.

> Выставить ручку для регулирования в hsh. Если запрошено больше лимита -
> отлуплять, если нет ручки - выдать столько, сколько в лимите написано.

Чем это будет удобнее чем есть сейчас? Сейчас у нас есть /tmp на tmpfs определённого размера (это и есть лимит для обычных пользовтаелей), если пакет хочет больше места, то процесс сборки обламывается пока админ не увеличит лимит.
Comment 19 Dmitry V. Levin 2008-08-30 02:38:13 MSD
(In reply to comment #18)
> (In reply to comment #17)
> > tmpfs нужного размера всегда можно выделить. Тогда не хост упадёт, а сборка
> > сломается.
> 
> Если я правильно понял Диму, то речь шла о автоматическом создании tmpfs и
> расположении там chroot.

Конечно, об автоматическом создании и удалении.
Причём основной выигрыш, помимо простоты использования, будет именно в существнном упрощении (в т.ч. с точки зрения защиты от атак со стороны пакетов) удаления чрута.

> В этом случае размер tmpfs и количество inodes предётся
> считать автоматически иначе в этом нет мысла.

Автоматически по объёму доступной виртуальной памяти.
Проблема в том, что избежать overcommit непросто (много пользователей,
и каждый может завести много таких чрутов),
а если не избежать, то можно устроить DoS на хост-систему.

Пойдём в devel?
Comment 20 Alexey Gladkov 2008-08-30 03:18:29 MSD
(In reply to comment #19)
> Конечно, об автоматическом создании и удалении.
> Причём основной выигрыш, помимо простоты использования, будет именно в
> существнном упрощении (в т.ч. с точки зрения защиты от атак со стороны
> пакетов) удаления чрута.

Значит я тебя правильно понял :)

> Автоматически по объёму доступной виртуальной памяти.
> Проблема в том, что избежать overcommit непросто (много пользователей,
> и каждый может завести много таких чрутов),

Если у каждого пользователя будет возможность создавать свои tmpfs, то overcommit не избежать.

Если сделать единое место учёта пользовательских tmpfs, то overcommit ты избежишь, но пользователи смогут DoS'ить друг друга... хотя и сейчас при желании пользователи могут это делать.

Но тут встают новые проблемы: Как делить память (tmpfs) на пользователей? Что делать, когда заводится новый пользователь, а лимит на память для пользователей исчерпан другими пользователями?

Конечно, эти проблемы можно решить, если примерно знать сколько пользователей ожидается на данном сервере, но динамичность всего решения "каждый chroot в tmpfs" сильно уменьшается и ложится на плечи админа.

Получается нечто подобное квотам... хотя почему подобное? Это именно квоты как есть, но по prefix'у каждого пользователя.

> а если не избежать, то можно устроить DoS на хост-систему.

Сейчас есть общий лимит tmpfs на /tmp и админ хост-системы может управлять общим количеством памяти, используемым под сборку.

> Пойдём в devel?

Пойдём.
Comment 21 Michael Shigorin 2009-02-23 18:09:02 MSK
(In reply to comment #19)
> а если не избежать, то можно устроить DoS на хост-систему.
Дяденьки, а дяденьки -- форкбомба уже не работает?  local DoS -- не то, чего стоит пытаться избежать любыми средствами, потому как слишком уж много вариантов на системе, которая хоть чем-то полезна.

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

> Пойдём в devel?
BTW у меня от него сейчас отпуск. :)