Oracle cloud: превращаем ubuntu 20.04 в gentoo

    Oracle cloud предлагает некоторые ресурсы совершенно бесплатно. В частности на халяву можно получить 2 виртуальные машины. При создании машины у вас есть выбор из centos, Ubuntu или oracle linux. С учетом ограниченности ресурсов витруальной машины мне стало интересно нельзя ли использовать на этой машине gentoo?

    В документации gentoo описано как можно на лету превратить любой линукс в gentoo. К сожалению инструкция последний раз обновлялась в 2014 и если ее применять в лоб скорее всего у вас возникнут проблемы. Однако на гитхабе можно найти скрипт, который по утверждению автора может в автоматическом режиме превратить любой линукс в gentoo. Скрипт давно не обновлялся, но после небольших изменений отработал как надо. Автор исходного скрипта решил не применять мой пулл реквест, но модифицировал свой скрипт базируясь на моих предложениях. Мой вариант скрипта можно найти тут.

    Итак, давайте осуществим превращение ubuntu 20.04 в gentoo. Для этого создаем виртуальную машину используя образ ubuntu 20.04 minimal и логинимся на него как пользователь ubuntu. После этого переключаемся на юзера root:

    sudo -i

    Переходим в режим single user:

    systemctl rescue

    В нормальных условиях при этом отваливается сеть. В oracle cloud этого не происходит, однако завершается процесс systemd-resolved и как следствие перестает работать dns. Давайте это исправим:

    rm /etc/resolv.conf && echo 'nameserver 8.8.8.8' >/etc/resolv.conf

    Теперь можно запустить скрипт миграции и пойти выпить чаю, это займет какое-то время:

    wget -qO- https://raw.githubusercontent.com/kt97679/to-gentoo/master/to-gentoo|bash

    Когда выполнения скрипта закончится он предложит вам перезагрузиться. Прежде чем это делать надо убедиться, что вы не потеряете root доступ после перезагрузки. Для этого надо разрешить доступ root по ssh:

    sed -i -e '/^PermitRootLogin.*/d' /etc/ssh/sshd_config && echo -e "\nPermitRootLogin without-password" >>/etc/ssh/sshd_config

    И поправить файл /root/.ssh/authorized_keys:

    sed -i -e 's/.*\(ssh-rsa.*\)/\1/' /root/.ssh/authorized_keys

    Теперь можно перезагружаться, но команда reboot не поможет, так что давайте привлечем тяжелую артиллерию:

    sync && echo 1 > /proc/sys/kernel/sysrq && echo b > /proc/sysrq-trigger

    Машина уходит в перезагрузку и через пару минут вы сможете залогиниться на нее по ssh как root. Вы находитесь в gentoo окружении, но по прежнему используете старые ядро и initrd. Давайте это исправим.

    Включим swap, без этого вам не хватит памяти скомпилировать новое ядро.

    fallocate -l2G /var/tmp/swap && chmod 0600 /var/tmp/swap && mkswap /var/tmp/swap && swapon /var/tmp/swap

    Я не планирую использовать на этой машине systemd, так что маскирую его и udev:

    echo -e 'sys-apps/systemd\nsys-fs/udev'> /etc/portage/package.mask/systemd

    После этого можно установить пакеты необходимые для компиляции ядра:

    emerge gentoo-sources app-arch/lz4

    Теперь можно перейти в директорию с исходниками ядра,

    cd /usr/src/linux

    сгенерировать конфиг нового ядра используя конфиг загруженного ядра,

    yes ""|make oldconfig

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

    yes ""|make localmodconfig

    Я планирую не использовать на этой машине initrd, так что все модули будут вкомпилированы в ядро:

    yes ""|make localyesconfig

    Запускаем компиляцию и установку ядра:

    make && make INSTALL_MOD_STRIP=1 modules_install && make install

    Наша машина весьма маломощна, так что этот процесс займет много времени. Когда компиляция закончится надо обновить конфигурацию загрузчика. Я добавил параметры ядра, которые применялись в исходной ubuntu.

    cat >/boot/grub/grub.cfg <<EOF
    set timeout=1
    menuentry 'gentoo' {
      linux $(ls -t /boot/vmlinuz-*|head -n1) root=/dev/sda1 console=tty1 console=ttyS0 nvme.shutdown_timeout=10 libiscsi.debug_libiscsi_eh=1
    }
    EOF

    Имеет смысл разрешить логин на последовательной консоли если будут проблемы с сетью:

    sed -i -e 's/^#\(.*ttyS0.*\)/\1/' /etc/inittab

    Осталось немного. После перезагрузки сетевой интерфейс будет называться не ens3, а eth0. Надо удалить скрипт инициализации старого интерфейса и добавить инициализацию нового:

    cd /etc/init.d && rm net.ens3 && ln -s net.lo net.eth0

    На случай необходимости залогиниться через последовательную консоль надо задать пароль для пользователя root:

    passwd

    Все готово, можно перезагружаться.

    Если после перезагрузки вам не удастся залогиниться на машину по ssh создайте консольное подключение и используйте его для отладки.

    Теперь у вас есть базовая установка gentoo которую можно модифицировать под ваши нужды. В системе остались артефакты от исходной ubuntu. Они больше не нужны и их можно удалить. Скрипты с командами миграции можно найти тут.

    Комментарии 36

      +2

      Но зачем? ;)

        +1
        Автор же написал это в первом абзаце.
          0

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

          +1
          Но это же интересно!
          0
          Тоже самое как LFS скриптом собирать, никакого удовольствия.

          Интереснее собрать gentoo в chroote по взрослому, потом на живой системе заменить корень на новую систему и ядро. С ораклом это довольно безопасно, у них терминал по типу kvm есть, хотя бы можно будет увидеть в чём косяк, если с ядром накосячить.
            +1
            можно ссылку на этот терминал? ищу и никак не найду
              +3
              Сведения об экземпляре
              image
            0
            Я думал о таком, но к сожалению у этой виртуалки слишком мало памяти, чтобы провернуть подобное если строить новый корень в tmpfs. Или вы предлагаете откусить кусок диска и строить новый корень там?
              0
              Ничего не надо откусывать и никакой tmpfs. Gentoo классическим путём устанавливается — распаковка stage3 в каталог, chroot, минимальная настройка — make.conf, профиль, локализация, fstab (можно подглядывать в «оригинальный»), пользователь. Дальше ядро, можно попробовать бинарное (в Gentoo теперь так можно), а можно и собрать по конфигу из оригинальной системы. А ещё лучше оригинальное оставить, никакого профита от своего ядра не будет, по идее в нём есть всё что нужно.

              А теперь самое интересное, в оригинальной системе гасим все сервисы (если что-то успели запустить), кроме своей ssh-сессии, и начинаем потихоньку, по каталогам (удаляем каталог и копируем), заменять корень на новый из каталога с Gentoo, например используя mc. Последними меняем /bin, /sbin. И перезагружаемся.

              Что может пойти не так? Только игры с ядром, если всё-таки собирали своё есть совсем ненулевая вероятность, что что-нибудь важное не включено.
                0
                Исходно скрипт to-gentoo именно это и делал: распаковывал stage3 в новый корень, монтировал туда /proc, /dev итд, выполнял там всю настройку и после этого копировал все в старый корень. Посмотрев на это мне показалось, что шаг с chroot лишний. Попробовал — и все сработало как надо. Можно попросить вас уточнить почему подход с chroot лучше подхода без него?
                  0
                  Мой первый комментарий:
                  Тоже самое как LFS скриптом собирать, никакого удовольствия.

                  Вариант с chroot даёт понимание как оно там «унутре» работает, что например можно запустить любое окружение независимо от базовой системы.
                    0
                    Так в данном случае нет разницы, так как мы уже подменили исходную систему.
            0
            но команда reboot не поможет
            а не пробовали systemctl reboot?
              0
              На момент перезагрузки systemctl от исходной ubuntu уже не в путях, так что вот прямо так не получится. Сработает ли если дать абсолютный путь к systemctl честно говоря не знаю, не пробовал.
                0
                Сработает.
              0
              Подскажите как в oracle cloud создать вторую машину — копию первой?
                +1
                docs.oracle.com/en-us/iaas/Content/Block/Tasks/cloningabootvolume.htm

                как я понимаю, с этого клона можно создать новый инстанс (раздел «Next Steps»)
                в отличие от бэкапа, который можно лишь подключить к другому инстансу в качестве несистемного диска
                  0
                  Да, все именно так и сработало.
                  Как раз пытался с бэкапа подключить и ничего не получалось.
                  Благодарствую.
                0
                Я не планирую использовать на этой машине systemd, так что маскирую его и udev:

                Что бы что?
                  0
                  Маскировка sytemd нужна, чтобы он не был установлен как зависимость другого пакета.
                    0
                    Я имел ввиду, с какой целью надо отказываться от systemd?
                      0
                      О, это персональный выбор конкретно для этого проекта. Разумеется, можно не маскировать systemd если он предпочтителен для ваших задач.
                        0
                        Меня просто всегда интересовало, отчего люди отказываются от, как минимум, неплохих инструментов.
                          +1
                          Это вы сейчас про какой инструмент, runinit, openrc, sysvinit, upstart?
                            0
                            systemd, внезапно!
                            +1
                            Вы затрагиваете очень холиварную тему. В интернете можно найти много материалов с критикой systemd. Причин не использовать его достаточно много.

                            Я откзался от systemd потому, что мне хотелось минималистическую систему, которая была бы проста для понимания. systemd тянет за собой слишком много зависимостей, так что использующую его систему сложно назвать минималистичной. Лично мне проще разобраться в скриптах openrc, чем в случае каких-то вопросов смотреть в исходники systemd.
                              +1
                              Основа systemd, это сам демон systemd, journald и udevd. Все остальные части systemd, так или иначе, можно менять (например на большинстве десктопных дистрибутивов вместо штатных networkd и resolved используется NetworkManager), хотя как по мне, лучше просто почитать маны, тем более что по качеству, систематизации и подачи материала редко какие маны можно с ними сравнить. А головняка systemd снимает очень много.
                                0
                                Вот список зависимостей systemd в gentoo.
                                  0
                                  Ну и? Порядка 30 зависимостей. При этом ничего монструозного.
                                  Примерно так-же как в Arch / Manjaro.
                                  image

                                  Причём половину, как минимум, так и так придётся ставить, в не зависимости от системы инициализации.
                                    0
                                    Как я уже сказал — вопрос личных предпочтений. Я хочу использовать openrc.
                    0
                    rm /etc/resolv.conf && echo 'nameserver 8.8.8.8' > /etc/resolv.conf

                    Может придирка, но зачем rm /etc/resolv.conf?
                      0
                      Потому что ubuntu 20.04 использует systemd-resolved и /etc/resolv.conf это симлинка на /run/systemd/resolve/stub-resolv.conf После перезагрузки этот файл не будет найден, что создаст проблемы для dhcp скрипта.
                        0
                        Вопрос есть ли разница между
                        rm /etc/resolv.conf && echo 'nameserver 8.8.8.8' > /etc/resolv.conf
                        и
                        echo 'nameserver 8.8.8.8' > /etc/resolv.conf
                          +1
                          Во втором случае мы обновим файл /run/systemd/resolve/stub-resolv.conf, который после перезагрузки исчезнет. Но симлинка останется, будет указывать на не существующий файл и при получении адреса по dhcp конфигурация днс не будет обновлена и как следствие днс не будет работать.
                      0
                      А чего бы просто не запустить новое ядро с initrd с помощью kexec, таким образом отвалившись от ФС и взяв под контроль всю машину сразу? ;)

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

                      Самое читаемое