Пытаюсь создать установочный USB-накопитель с cloudinit для создания машин с двойной загрузкой.

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

Мы используем cloudinit для автоматической установки Ubuntu как второй операционной системы на машинах, где уже установлена Windows 10. Мы делаем это, освобождая место в конце диска, уменьшая раздел Windows.
Для установки Linux на свободное место файл user-data создает shell-скрипт, который анализирует конфигурацию диска и добавляет её в autoinstall.yaml.
Это хорошо работало с Ubuntu 20_04 и 22_04 с Windows 10. Наш существующий user-data скрипт работает, но он не может найти правильный раздел и, следовательно, удаляет раздел Windows и использует весь диск, поэтому нет двойной загрузки. Это начало диагностики, но кто-нибудь еще пытается это сделать? Для сведения, нам нужно сделать ~550 машин как часть учебных кластеров факультета компьютерных наук.
Это работало последние три года, включая изменение версии Ubuntu, поэтому не уверены, связано ли это с изменениями на стороне Ubuntu или Windows 11.

Я знаю, что Microsoft не любит двойную загрузку, но я отправляю это с машины с двойной загрузкой Win 11/Ubuntu 24_04, которую я установил полностью вручную.

Ниже представлена часть файла user-data

# создано для 24_04
# задачи
# попробовать удалить snap
write_files:
  - path: /root/partitions.sh
    permissions: '0700'
    content: |
      #!/bin/bash
      # Чтение текущей таблицы разделов диска и запись секции хранения user-data, которая сохраняется как /autoinstall.yaml
      # Используем printf для записи текстовых секций в /autoinstall.yaml, так как нам нужны начальные пробелы

      # Запись секции диска - принимает один аргумент
      # $1 = расположение, где диск для установки смонтирован в файловой системе Linux, например /dev/nvme0n1, /dev/sda
      print_disk () {
      printf '%s\n' \
      "storage:" \
      "  config:" \
      "  - ptable: gpt" \
      "    path: $1" \
      "    preserve: true" \
      "    name: ''" \
      "    grub_device: false" \
      "    type: disk" \
      "    id: disk-$device" >> /autoinstall.yaml
      }

      # Запись секции разделов - требуется три аргумента
      # $1 = размер раздела в байтах
      # $2 = номер раздела - используется внутри автопоиска
      # $3 = это EFI-раздел?
      print_partition () {
      printf '%s\n' \
      "  - device: disk-$device" \
      "    size: $1" \
      "    number: $2" \
      "    preserve: true" \
      "    grub_device: $3" \
      "    type: partition" \
      "    id: partition-$device$pname$2"  >> /autoinstall.yaml
      }

      # Запись секции форматирования - требуется только для разделов / и /boot/efi
      # $1 = vfat для EFI или ext4 для /
      # $2 = сохранить EFI-раздел, не сохранять /
      print_format () {
      printf '%s\n' \
      "  - fstype: $1" \
      "    volume: partition-$device$pname$part" \
      "    preserve: $2" \
      "    type: format" \
      "    id: format-$part" >> /autoinstall.yaml
      }

      # Запись команд монтирования для EFI и / разделов
      print_mount () {
      printf '%s\n' \
      "  - path: $1" \
      "    device: format-$part" \
      "    type: mount" \
      "    id: mount-$part" >> /autoinstall.yaml
      }

      # Определить самый большой диск и предположить, что это цель для установки
      disk=`lsblk -dln -o path -x size | tail -n 1`
      device=`echo $disk | cut -d "https://askubuntu.com/" -f3`

      # если nvme, добавить 'p'
      pname=""
      if [ "$device" != "sda" ];then
        pname=p
      fi

      # Найти общее количество разделов
      num_parts=`fdisk -l $disk | grep "^$disk$pname[0-9]" | wc -l`

      # Найти EFI-раздел, который создала Windows
      efi_part=`fdisk -l $disk | grep "EFI" | awk '{print $1}' | tail -n 2`

      # Записать информацию о диске
      print_disk $disk

      # Итерация по разделам
      for part in `seq $num_parts`
        do
        if [ "$disk$pname$part" = "$efi_part" ]
            # Это EFI-раздел
            then
            print_partition `lsblk -lbn -o type,size $disk$pname$part | grep part | awk '{print $2}'` $part "true"
            printf "    flag: boot\n" >> /autoinstall.yaml # Дополнительная строка для EFI-раздела
            print_format vfat "true"
            print_mount "/boot/efi"
        else
            # Все остальные разделы
            print_partition `lsblk -lbn -o type,size $disk$pname$part | grep part | awk '{print $2}'` $part "false"
        fi

        if [ "$part" == "$num_parts" ]
            # Это последний раздел, который мы предполагаем будет использоваться для Ubuntu
            then
            printf "    wipe: superblock\n" >> /autoinstall.yaml # Дополнительная строка для секции разделов из вышеописанной if...else...
            print_format ext4 "false"
            print_mount "/"
        fi
        done
      printf "...\n" >> /autoinstall.yaml # Добавьте эту строку в конце, чтобы обозначить конец файла для установщика

autoinstall:
  early-command:
    - sed -i '$d' /autoinstall.yaml
    - /root/partition.sh
  user-data:
    timezone: Europe/London
    hostname: localhost

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

Теория

Создание загрузочной флешки с помощью Cloudinit для установки Ubuntu в рамках системы с двойной загрузкой на устройствах, где уже установлена Windows 10, — это задача, требующая внимания к деталям и адаптации скриптов для настройки правильной конфигурации. Cloudinit является мощным инструментом автоматизации, который позволяет программно выполнять такие установки. Однако с переходом на новые версии операционных систем, таких как Ubuntu 24.04 и Windows 11, могут возникнуть проблемы с конфигурацией, которые необходимо решать.

Пример

Вы столкнулись с проблемой, когда ваш сценарий установки больше не находит правильный раздел диска и, как следствие, перезаписывает весь диск, включая раздел с Windows. Для решения этой проблемы нужно детально изучить и адаптировать скрипт на основе новых системных изменений и особенностей работы с GPT-дисками, особенно если используется оборудование с nvme-дисками.

Ваш текущий скрипт partitions.sh, который генерирует файл /autoinstall.yaml, должен считывать текущее состояние дисков и предлагать конфигурацию нового раздела для Ubuntu. Тем не менее, изменения в управляющем программном обеспечении или особенностях HD могут привести к неправильному распознаванию разделов или параметров конфигурации. Скрипты, работающие с заголовками и флагами разделов, часто оказываются чувствительными к подобным изменениям.

Применение

  1. Адаптация Скрипта:

    • Убедитесь, что ваш скрипт верно получает имя устройства. Используя lsblk и fdisk, следует удостовериться, что вывод данных соответствует актуальным особенностям системного диска. Проверка точности команд парсинга и использованных аргументов, таких как tail и grep, критично важна.

    • Проверьте логику цикла поиска efi-раздела. Возможно, вам стоит использовать более расширенные инструменты для парсинга, такие как parted, чтобы более точно определять типы и параметры разделов.

    • Убедитесь в правильности работы блока, где проверяется и устанавливается флаг boot. Это может стать причиной для неверного указания точки загрузки ОС, что важно в сценарии Dual Boot.

  2. Комплексное тестирование:

    • Для диагностики и исправления ошибок используйте тестовое оборудование, чтобы выполнять двойные установки с различными конфигурациями одновременной установки Windows и Ubuntu. Эмулируйте раздел диска, как в реальных условиях.

    • Проводите контроль изменений конфигурационных файлов перед финальной перезаписью. Это поможет выявить моменты, на которых нарушается логика создания разделов.

  3. Документация и логирование:

    • Рассмотрите возможность введения более детального логирования в ваш скрипт. Храните лог-файлы, чтобы было легко обнаруживать и устранять неполадки.

    • Обратитесь к документации Ubuntu и Microsoft по работе с dual boot для новых версий ОС. Иногда официальные обновления содержат важные изменения и инструкции, которые могут направить на решение проблемы.

  4. Обработка исключений и альтернатива:

    • Предусмотрите дополнительные механизмы проверки конфигурации монтирования. Например, использование blkid для добавления проверок, которые более надежно идентифицируют устройства и разделы благодаря уникальным идентификаторам UUID.

    • Рассмотрите возможность альтернативного подхода: применение технологий контейнеризации или виртуализации как временного решения, если проблема с dual boot остается нерешенной на физическом уровне.

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

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

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