ConnectX-3 VPIなんですが、uefi の rom はあるだろうと思っていたのですが、調べた所、どうやら Legacy rom しかないらしく、セキュアーブートはできないのですが、ipoib 経由で iSCSI root はできたので、備忘録として挙げてみることにしました。
まず、大まかな流れですが、iSCSI target 上で disk イメージを作成し targetcli をつかってアクセスできるようにしておきます。 なお disk imageは uefiクライントも共有できるように gptでパーティションを作成し grub(uefi) を設定していますが、今回は pxelinux が kernel と initrd を直接読み込むので問題はありません。
次に、ConnectX-3の場合 ブートデバイスとして起動すると、flexboot ( iPXE ) が立ち上がるのですが、Legacy ブート なのでサーバ側は 前述のように grub ではなく、 pxelinux を tftp サーバ上で設定します。なお今回は menu.ipxe 経由で disk イメージを iSCSIデバイスとしてフックして iBFT を登録させておいてから、 pxelinux にhttpでチェーンするようにしました。( http server ( apache2 ) の設定は前回を参照してください。)
次に、dhcp サーバを設定し、menu.ipxe を取得できるようにしておきます。なお、dhcpサーバーについては、残念ながら Debian 12 の isc-dhcp-server 場合 ipoib での bootp/dhcp には対応しておらず、今回は Ubuntu 24.04 LTS で構成しました。また今回はiSCSIターゲットは 別セグメントにありますが、dhcpd.conf が正しく default gw を指定しルーティングが機能していれば問題はありません。
以下設定詳細です。iSCSI イニシエータ(クライアント) が 10.1.40.112/sv112, iSCSI ターゲット(サーバ)が10.1.56.106/sv106, tftp/httpサーバが10.1.40.50/i50としています。
まず、iSCSI ターゲット上で disk imageを作成しておきます。
最後は isc-dhcp-server ( /etc/dhcp/dhcpd.conf ) です。ここでは 固定アドレス、 iscsi-initiator-iqn、取得する file を指定します。
作業は以上です。ConnectX-3 VPIをブートデバイスにし、menu.ipxe -> pxelinux.cfg -> iSCSI root の順に起動できれば OK です。
ConnectX-3 は uefiに対応していないのは残念ですが、ConnextX-4以降は対応しているので、これで大丈夫そうです。
今回は以上です。それでは。
まず、大まかな流れですが、iSCSI target 上で disk イメージを作成し targetcli をつかってアクセスできるようにしておきます。 なお disk imageは uefiクライントも共有できるように gptでパーティションを作成し grub(uefi) を設定していますが、今回は pxelinux が kernel と initrd を直接読み込むので問題はありません。
次に、ConnectX-3の場合 ブートデバイスとして起動すると、flexboot ( iPXE ) が立ち上がるのですが、Legacy ブート なのでサーバ側は 前述のように grub ではなく、 pxelinux を tftp サーバ上で設定します。なお今回は menu.ipxe 経由で disk イメージを iSCSIデバイスとしてフックして iBFT を登録させておいてから、 pxelinux にhttpでチェーンするようにしました。( http server ( apache2 ) の設定は前回を参照してください。)
次に、dhcp サーバを設定し、menu.ipxe を取得できるようにしておきます。なお、dhcpサーバーについては、残念ながら Debian 12 の isc-dhcp-server 場合 ipoib での bootp/dhcp には対応しておらず、今回は Ubuntu 24.04 LTS で構成しました。また今回はiSCSIターゲットは 別セグメントにありますが、dhcpd.conf が正しく default gw を指定しルーティングが機能していれば問題はありません。
以下設定詳細です。iSCSI イニシエータ(クライアント) が 10.1.40.112/sv112, iSCSI ターゲット(サーバ)が10.1.56.106/sv106, tftp/httpサーバが10.1.40.50/i50としています。
まず、iSCSI ターゲット上で disk imageを作成しておきます。
# on iSCSI target (10.1.56.106 106) apt-get install targetcli-fb qemu-utils mkdir -p /srv/deb01 cd /srv/deb01 dd if=/dev/zero of=deb12.disk.img bs=1024k count=32768 NBD=nbd0 modprobe -av nbd qemu-nbd -f raw -c /dev/${NBD} deb12.grub.img # パーティションの作成 fdisk ############################ g n enter enter 1050623 t uefi n enter enter enter w ############################ mkfs.vfat /dev/${NBD}p1 # debian 10 の場合 # mkfs.xfs -m crc=0,finobt=0 -f /dev/${NBD}p2 # debian 12 の場合 mkfs.xfs -f /dev/${NBD}p2 P2_UUID=`xfs_admin -u /dev/${NBD}p2 | cut -d' ' -f 3` # uefi クライアントと共通で使うので efi ファイルと grub をインストール mount /dev/${NBD}p2 /mnt mkdir -p /mnt/boot/efi mount /dev/${NBD}p1 /mnt/boot/efi cd /mnt/boot/efi mkdir -p /mnt/boot/efi/EFI/debian cd /srv/deb01 mkdir netboot cd netboot wget https://ftp.debian.org/debian/dists/stable/main/installer-amd64/current/images/netboot/netboot.tar.gz tar xzpf netboot.tar.gz cp -a debian-installer/amd64/bootnetx64.efi /mnt/boot/efi/EFI/debian/ cat > /mnt/boot/efi/EFI/debian/grub.cfg <<EOF search.fs_uuid $P2_UUID root hd0,gpt2 set prefix=(\$root)/boot/grub configfile \$prefix/grub.cfg EOF cat > /mnt/boot/grub/grub.cfg <<EOF menuentry 'Debian 12 iSCSI root'{ linux /vmlinuz root=UUID=$P2_UUID rw ip=::::::dhcp iscsi_auto rootfstype=xfs rootwait initrd /initrd.img } EOF grub-install --target=x86_64-efi --efi-directory=/mnt/boot/efi --boot-directory=/mnt/boot --uefi-secure-boot /dev/${NBD} # disk image の population # on iscsi target ( 10.1.56.106 sv106 ) cd /mnt # debian 10 busterの場合 # debootstrap buster . # debian 12 boookworm の場合 debootstrap bookworm . # debootstrap では足りないパッケージ等を半自動でインストール・設定 cat > root/and-so-on.sh <<EOF apt-get install -y --no-install-recommends linux-image-amd64 linux-image-6.1.0-29-amd64 busybox xfsprogs openssh-server open-iscsi zstd apt-get install -y --no-install-recommends locales console-setup fbterm fonts-vlgothic fonts-courier-prime # set root password passwd # add user adduser YourUserName # change hostname echo deb12a > /etc/hostname # add ipv4 nameservers echo nameserver 10.1.1.64 >> /etc/resolv.conf echo nameserver 10.1.1.65 >> /etc/resolv.conf # setup locales dpkg-reconfigure locales # setup keyboard layout dpkg-reconfigure keyboard-configuration exit EOF mount -t proc proc proc/ mount -t sysfs sysfs sys/ chroot . bash root/and-so-on.sh umount proc/ umount sys/ # カーネル等を tftp/http サーバにコピー scp /mnt/boot/*6.1.0-29* 10.1.56.50:/srv/tftp/boot/disk imageの作成が済んだら targetcliでアクセスできるようにしておきます。
apt-get install targetcli-fb targetcli /backstores/fileio create deb12-amd64-01 /srv/deb01/deb12.disk.img targetcli /iscsi create iqn.1868-01.com.example:sv106.deb12-amd64-01 targetcli /iscsi/iqn.1868-01.com.example:sv106.deb12-amd64-01/tpg1/luns create /backstores/fileio/deb12-amd64-01 targetcli /iscsi/iqn.1868-01.com.example:sv106.deb12-amd64-01/tpg1/acls create iqn.1868-01.com.example:sv112続いて menu.ipxeとpxelinux.cfg/sv112 (sv112は今回のiSCSIイニシエータ) を作成します。
# on tftp server (10.1.40.50 i50) cat > /srv/tftp/menu.ipxe <<EOF #!ipxe :start menu MENU item --gap -- -------------- item pxelinux boot from http://10.1.40.50/pxelinux.0 item --gap -- -------------- item shell Drop to iPXE shell item --gap -- -------------- choose selected goto ${selected} :pxelinux set root-path iscsi:10.1.56.106::::iqn.1868-01.com.example:sv106.deb12-amd64-01 sanhook ${root-path} set 209:string pxelinux.cfg/${hostname} set 210:string http://${next-server}/ chain http://${next-server}/pxelinux.0 || goto start :shell echo Type 'exit' to get back to the menu shell set menu-timeout 0 goto start EOF # on tftp server (10.1.40.50 i50) apt-get install syslinux pxelinux tftpd-hpa cd /srv/tftp cp -a /usr/lib/syslinux/modules/bios/menu.c32 . cp -a /usr/lib/syslinux/modules/bios/ldlinux.c32 . cp -a /usr/lib/syslinux/modules/bios/libutil.c32 . cp -a /usr/lib/PXELINUX/pxelinux.0 . mkdir pxelinux.cfg # pxelinux の menu を作成 cat > pxelinux.cfg/sv112 <<EOF PROMPT 1 TIMEOUT 100 UI menu.c32 SERIAL 0 115200 MENU TITLE PXE Boot Menu MENU DEFAULT 6.1.0-29 LABEL 6.1.0-29 kernel /boot/vmlinuz-6.1.0-29-amd64 append initrd=/boot/initrd.img-6.1.0-29-amd64.ib root=UUID=72cd4ba4-d447-4118-8e35-xxxxxxxxxxxx ip=::::::dhcp iscsi_auto net.ifnames=0 rootfstype=xfs rw console=tty0 console=ttyS0,115200n8 EOFつづいて initrd を 作成し配置します。(今回はiSCSIターゲット sv106 が Debian 12 なのでこちらで作業)
# edit /etc/initramfs-tools/modules cat >> /etc/initramfs-tools/modules EOF iscsi_ibft ib_core ib_cm ib_uverbs ib_umad iw_cm rdma_cm rdma_ucm mlx4_core mlx4_ib ib_mthca ib_ipoib EOF # patch for /usr/share/initramfs-tools/scripts/local-top/iscsi ## ----------------------------------------------------------- --- iscsi.orig 2025-03-18 07:16:13.081164264 +0900 +++ iscsi.ok.02.2 2025-03-26 22:37:00.263868546 +0900 @@ -99,7 +99,7 @@ # try to auto-configure network interface based # on firmware values modprobe iscsi_ibft - iscsistart -N + iscsistart -N || echo "Unable to configure network" # write out /run/net-$IFACE.conf based on what # was in the firmware @@ -182,7 +182,7 @@ # also, if we set up DHCP iBFT, we need ipconfig to run so it creates # a proper /run/net-${DEVICE}.conf file that includes the DNS search # domain, which we don't get in our iBFT data (see LP: #1806777) - configure_networking + true || configure_networking if [ -n "$IBFT_DHCP_DEVICE" ]; then if ! [ -e "/run/net-${DEVICE}.conf" ] ; then @@ -192,7 +192,7 @@ # though that will not include the DNS search domain mv "/run/net-${DEVICE}.conf.ibft" "/run/net-${DEVICE}.conf" # need to re-run configure_networking to process conf file - configure_networking + true || configure_networking fi fi @@ -330,8 +330,58 @@ exit 0 fi +modprobe iscsi_ibft +iscsistart -f | grep -v \# > /run/iscsi-vars +iface=`cat /run/iscsi-vars | grep iface.net_ifacename | cut -d' ' -f3` + +if [ "$iface" == "$DEVICE" ]; then + iscsistart -N || echo Failed to bring up the network as specified by iBFT +else + i=$DEVICE + if [ -e /sys/class/net/$i/carrier ]; then + ip link set dev $i up && interface_up=`cat /sys/class/net/$i/carrier` + else + interface_up="" + fi + echo awainting for interface $i up + count=0 + while [ "$interface_up" == "0" -o ! -n "$interface_up" ] && [ $count -lt 30 ] + do + echo interface_up: $interface_up + if [ -e /sys/class/net/$i/carrier ]; then + ip link set dev $i up && interface_up=`cat /sys/class/net/$i/carrier` + else + interface_up="" + fi + if [ "$interface_up" == "1" ];then + echo $i is up + fi + count=$((count + 1)) + sleep 1 + done + + address=`cat /run/iscsi-vars | grep iface.ipaddress | cut -d' ' -f3` + netmask=`cat /run/iscsi-vars | grep iface.subnet_mask | cut -d' ' -f3` + gateway=`cat /run/iscsi-vars | grep iface.gateway | cut -d' ' -f3` + plength=`cat /run/iscsi-vars | grep iface.prefix_len | cut -d' ' -f3` + dns=`cat /run/iscsi-vars | grep iface.primary_dns | cut -d' ' -f3` + + ip addr del $address/$plength dev $iface + ip addr add $address/$plength dev $DEVICE + ip rout add default via $gateway + + initiatorname=`cat /run/iscsi-vars | grep iface.initiatorname | cut -d' ' -f3` + targetname=`cat /run/iscsi-vars | grep node.name | cut -d' ' -f3` + targetaddr=`cat /run/iscsi-vars | grep node | grep address | grep 0 | cut -d' ' -f3` + iscsistart --param iface.net_ifacename=ib0 -i $initiatorname -g 1 -t $targetname -a $targetaddr || true +fi + do_iscsi_login +if [ "$iface" != "$DEVICE" ]; then + ip addr del $address/$plength dev $iface +fi + udevadm settle # The second check is to allow us to use multiple root= parameters. That way##----------------------------------------------------------- # create a config file cat > /etc/iscsi/iscsi.initramfs <<EOF ISCSI_AUTO=true EOF # edit /etc/initramfs-tools/initramfs.conf --- /etc/initramfs-tools/initramfs.conf.orig 2022-06-20 20:54:17.000000000 +0000 +++ /etc/initramfs-tools/initramfs.conf 2025-03-25 04:03:02.511800529 +0000 @@ -63,7 +63,7 @@ # Overridden by optional ip= or BOOTIF= bootarg # -DEVICE= +DEVICE=ib0 # # NFSROOT: [ auto | HOST:MOUNT ] # initrd の作成と tftp/http サーバへの配置 mkdir ~/initrd_ib cd ~/initrd_ib update-initramfs -k 6.1.0-29-amd64 -c -b . mv initrd.img-6.1.0-29-amd64 initrd.img-6.1.0-29-amd64.ib scp initrd.img-6.1.0-29-amd64.ib root@10.1.56.50:/srv/tftp/boot/追記:シングルインターフェースの場合問題ないのですが、デュアルインターフェースの場合、ib0ではなくib1が選択される場合があります。initramfs の local-top/iscsi スクリプトを追ったのですがどうやら iBFT の値の受け渡しに問題があるようなので、local-top/iscsi スクリプトに簡易ワークアラウンドを追加しました。
最後は isc-dhcp-server ( /etc/dhcp/dhcpd.conf ) です。ここでは 固定アドレス、 iscsi-initiator-iqn、取得する file を指定します。
allow booting; allow bootp; option iscsi-initiator-iqn code 203 = string; option space pxelinux; option pxelinux.magic code 208 = string; option pxelinux.configfile code 209 = text; option pxelinux.pathprefix code 210 = text; option pxelinux.reboottime code 211 = unsigned integer 32; set vendorclass = option vendor-class-identifier; option pxe-system-type code 93 = unsigned integer 16; set pxetype = option pxe-system-type; default-lease-time 600; max-lease-time 7200; ddns-update-style none; authoritative; log-facility-local7; subnet 10.1.40.0 netmask 255.255.255.0 { option domain-name-servers 10.1.1.64; option domain-name "example.com"; option routers 10.1.40.50; option broadcast-address 10.1.40.255; next-server 10.1.40.50; if substring(vendorclass, 0, 9)="PXEClient" { if pxetype=00:06 or pxetype=00:07 { filename "ipxe-signed/ipxe.efi"; # filename "ipxe-signed/snponly.efi"; } else { filename "menu.ipxe"; } } pool { range 10.1.40.200 10.1.40.250; }guid (00:02:c9:03:00:18:2f:91) } host sv112 { option host-name "sv112"; hardware ethernet 02:02:c9:18:2f:91; option dhcp-client-identifier=ff:00:00:00:00:00:02:00:00:02:c9:00:00:02:11:22: 33:44: 55:66; fixed-address 10.1.40.112; next-server 10.1.40.50; filename "menu.ipxe"; # filename "pxelinux.0"; # option pxelinux.configfile "pxelinux.cfg/sv112"; option iscsi-initiator-iqn "iqn.1868-01.com.example:sv112"; # option root-path "iscsi:10.1.56.106::::iqn.1868-01.com.example:sv106.deb12-amd64-01"; }dhcp-client-identifierは 接頭 ff:00:00:00:00:00:02:00:02:c9:00: + GUID 8バイト(00:02:11:22:33:44:55:66)です。編集が済んだら、systemctl restart isc-dhcp-server とします。
作業は以上です。ConnectX-3 VPIをブートデバイスにし、menu.ipxe -> pxelinux.cfg -> iSCSI root の順に起動できれば OK です。
ConnectX-3 は uefiに対応していないのは残念ですが、ConnextX-4以降は対応しているので、これで大丈夫そうです。
今回は以上です。それでは。
コメント
コメントを投稿