2025-07-03
NixOSのKernel Moduleロード順序
NixOSで起動時に明示的にKernel Moduleをロードする場合,以下のようなConfigurationを記述する.
# 通常のロード
boot = {
kernelModules = [
"nvidia"
"nvidia_modeset"
"nvidia_drm"
"nvidia_uvm"
];
}
# initrdでの早期ロード
boot = {
initrd.kernelModules = [
"nvidia"
"nvidia_modeset"
"nvidia_drm"
"nvidia_uvm"
];
}
これは単純なlistOf string
である.
従来,kernelModules
の値は出現順に並んだままinit scriptに渡り,modprobe
されていた.
しかし,以下のPRの変更により,ロード順序がalphabetical orderとなり,従来効いていたlib.mkOrder
によるプライオリティも機能しなくなってしまった.
https://github.com/NixOS/nixpkgs/pull/375975
これはkernelModules
などの型をboolean
を値をして持つattrSet
としても扱えるようにする変更で,モジュールのロード可否を柔軟に制御可能となる.
しかし,内部的にはattrSet
として扱われるようになり,順序に関係なく等価なものとして扱われるため,list
として取り出した際に勝手にアルファベット順となってしまう.lib.mkOrder
もあくまでマージの際の優先度を決めるものであり,マージ後の状態には関与しない.
見かけ上後方互換性があるように見えるが,実際は破壊的な変更である.
PCI Passthrough on the NixOS Hostで書いたように,私はPCI Passthroughを使用する環境を持っているため,モジュールのロード順序を制御できないと致命的である.
自分の知識では解決策が思いつかなかったため,issueを立ててみたところ,softdep
をmodprobe
の設定に入れてはどうかという提案を受けた.私の環境ではこれがベストな解決策であり,正しく動作した.
以下のようにvfio関連のモジュールをavailableKernelModules
に移動し,extraModprobeConfig
でnvidia
モジュールの依存に追加した.
boot = {
initrd.availableKernelModules = [
"pci_stub"
"vfio_pci"
"vfio_iommu_type1"
"vfio"
];
# fix for module load order
extraModprobeConfig = ''
softdep nvidia pre: pci_stub vfio vfio_iommu_type1 vfio_pci
'';