Записи в Diskfilter не поддерживаются> Что вызывает эту ошибку?
Это сообщение появляется при выходе из меню Grub и перед заставкой Ubuntu.
Как мне исправить проблему, чтобы очистить сообщение?
И что это значит?
error: Diskfilter writes are not supported
Система загружается и, кажется, работает просто отлично.
2 ответа
Это ошибка!
Эта ошибка возникает в самой последней версии Ubuntu Server LTS (Ubuntu Server 14.04 LTS), когда вы создаете загрузочный раздел (или корневой раздел, если загрузочный раздел не существует) внутри LVM или раздела RAID.,
Вы можете получить больше информации об этой ошибке в Ubuntu Launchpad: Ошибка #1274320 "Ошибка: запись в дисковый фильтр не поддерживается".
Обновление: эта ошибка уже исправлена в Ubuntu Server 14.04 и некоторых более новых версиях Ubuntu. Вероятно, вам нужно всего лишь запустить apt-get upgrade
,
Почему эта ошибка возникает?
Когда система загружается, GRUB читает (load_env
) данные в /boot/grub/grubenv
, Этот файл называется GRUB Environment Block.
Из руководства GRUB:
Часто полезно иметь возможность запомнить небольшое количество информации от одной загрузки к другой.
[...]
Во время загрузки команда load_env (см. Load_env) загружает из нее переменные среды, а команда save_env (см. Save_env) сохраняет в ней переменные среды.
[...]
grub-mkconfig
использует эту возможность для реализацииGRUB_SAVEDEFAULT
Такое поведение может быть основано на /etc/grub.d/00_header
(update-grub
использует этот файл для генерации /boot/grub/grub.cfg
файл):
if [ -s $prefix/grubenv ]; then
set have_grubenv=true
load_env
fi
Проблема в том, что save_env
Оператор работает только в простых установках (вы не можете запустить save_env
внутри диска RAID или LVM). Из руководства GRUB:
По соображениям безопасности это хранилище доступно только при установке на простом диске (без LVM или RAID), с использованием файловой системы без контрольной суммы (без ZFS) и с использованием функций BIOS или EFI (без ATA, USB или IEEE1275).
Функция записи GRUB использует save_env
оператор для обновления состояния ошибки записи (см. Справку Ubuntu - Grub 2, раздел "Последняя загрузка не удалась или загрузка в режим восстановления"). Однако в Ubuntu 14.04 (и в последних версиях Debian) save_env
оператор (внутри функции recordfail) используется, даже если GRUB установлен в LVM или RAID.
Давайте посмотрим линии от 104 до 124 в /etc/grub.d/00_header
:
if [ "$quick_boot" = 1 ]; then
[...]
case "$FS" in
btrfs | cpiofs | newc | odc | romfs | squash4 | tarfs | zfs)
cat <<EOF
# GRUB lacks write support for $FS, so recordfail support is disabled.
[...]
if [ -n "\${have_grubenv}" ]; then if [ -z "\${boot_once}" ]; then save_env recordfail; fi; fi
GRUB корректно пропускает функцию ошибки записи при использовании неподдерживаемых файловых систем (btrfs, zfs и т. Д.), Ноне пропускает LVM и RAID в любой момент.
Как GRUB защищает себя от записи внутри RAID и LVM?
Для правильного чтения / записи в файловых системах GRUB загружает соответствующий модуль.
GRUB использует модульдискового фильтра(insmod diskfilter
) в разделах RAID и модульlvm в разделах LVM.
Давайте посмотрим реализацию чтения / записи модуляdiskfilter:
apt-get source grub2
vim grub2-2.02~beta2/grub-core/disk/diskfilter.c
Я вставляю код здесь (строки от 808 до 823). Предупреждение, показанное в этом вопросе, появляется в строке 821:
static grub_err_t
grub_diskfilter_read (grub_disk_t disk, grub_disk_addr_t sector,
grub_size_t size, char *buf)
{
return read_lv (disk->data, sector, size, buf);
}
static grub_err_t
grub_diskfilter_write (grub_disk_t disk __attribute ((unused)),
grub_disk_addr_t sector __attribute ((unused)),
grub_size_t size __attribute ((unused)),
const char *buf __attribute ((unused)))
{
return grub_error (GRUB_ERR_NOT_IMPLEMENTED_YET,
"diskfilter writes are not supported");
}
grub_diskfilter_read
функция реализована (и GRUB может читать файловые системы RAID). Тем не менееgrub_diskfilter_write
функция поднимает GRUB_ERR_NOT_IMPLEMENTED_YET
ошибка.
Почему используетсяquick_boot=0
решать проблему? И почему это неправильное решение?
Если вы посмотрите еще раз в/etc/grub.d/00_header
код, вы увидите, что признак записи не используется, только когдаquick_boot=1
, Итак, меняя quick_boot
от 1 до 0 отключает функцию отсутствия записи и отключает запись в раздел RAID/LVM.
Тем не менее, он также отключит многие другие функции (запуститьgrep \$quick_boot /etc/grub.d/*
и вы увидите). Еще больше, если однажды вы поменяете/boot/grub
вне RAID/LVM, функция записи по-прежнему будет отключена.
В общем, это решение без необходимости отключает функции, и оно не является универсальным.
Какое правильное решение?
Правильное решение должно рассмотреть возможность отключенияsave_env
операторы, когда GRUB находится внутри разделов LVM или RAID.
В системе Debian Bug Tracker был предложен один патч для реализации этого решения. Его можно найти по адресу: https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=754921
Идея этого патча заключается в следующем:
- Запустить
grub-probe --target=abstraction "${grubdir}"
команда, чтобы узнать, какие модули абстракции GRUB использует для чтения / записи файлов в/boot/grub
каталог; - Если GRUB использует
diskfilter
или жеlvm
модуль, пропустите записьsave_env
заявление и написать соответствующий комментарий в/boot/grub/grub.cfg
файл;- Например,
# GRUB lacks write support for /dev/md0, so recordfail support is disabled.
- Например,
Как правильно применить решение?
Если вы не хотите ждать, пока этот патч будет применен ребятами из Ubuntu/Debian в официальном коде, вы можете использовать мой патч 00_header
:
# Download
wget https://gist.githubusercontent.com/rarylson/da6b77ad6edde25529b2/raw/99f266a10e663e1829efc25eca6eddb9412c6fdc/00_header_patched
# Apply
mv /etc/grub.d/00_header /etc/grub.d/00_header.orig
mv 00_header_patched /etc/grub.d/00_header
# Disable the old script and enable the new one
chmod -x /etc/grub.d/00_header.orig
chmod +x /etc/grub.d/00_header
# Update Grub
update-grub
Я думаю, что эта ошибка возникает из-за рейда или LVM раздела.
Для временного решения этой проблемы:
Редактировать:/etc/grub.d/10_linux
замещать 'quick_boot="1"' with 'quick_boot="0"'
Затем:
sudo update-grub