Booten vom Netzwerk #
Manchmal kann es interessant sein, einen Rechner komplett über das Netzwerk zu booten, d.h. ohne jede Festplatte, CD oder ähnliches. Dies hat zum einen den Vorteil, dass man diese Komponenten spart (was Geld, Platz im Rechner z.B. in embedded Devices und Zeit bei der Installation spart), zum anderen kann man auf diese Art und Weise aber auch einen ganzen Park von Rechnern zentral verwalten, da viele Rechner letztlich nur auf ein einziges installiertes System zugreifen.
Andere Artikel zum Thema sind auch DisklessClient und LinuxTerminalServer. Dieses Verfahren wird z.B. auch vom DBoxLinux angewandt, da die D-Box keinerlei Laufwerke besitzt.
Grundsätzlicher Ablauf #
Zuerst wird entweder vom BIOS oder von einem Boot-ROM auf der Netzwerkkarte aus der Netboot-Vorgang gestartet. Alternativ kann dies auch von einer Diskette aus geschehen.
Das Boot-BIOS holt sich per bootp (ähnlich NetzKonfigMitDHCP) die Netzwerkparameter des Netzes und den Dateinamen eines Bootimages. Dieses Bootimage wird dann per TFTP (eine Art vereinfachtes FTP-Protokoll) vom Server gelesen.
Dieses Bootimage kann nun entweder direkt ein Linux-Kernel sein, der sodann sofort loslegt oder ein Bootloader, mit dessen Hilfe man dann einen Kernel auswählen und "nachladen" kann.
Der Kernel muss nun einige Teile fest einkompiliert haben, z.B. den Netzwerkkarten-Treiber sowie die NFS-Unterstützung, da er ja zuerstmal kein root-Filesystem hat. Nun wird dem Kernel der Name einer NFS-Freigabe übergeben, die er als root-Filesystem nimmt. Dieses mountet er, sucht dort das init-Programm und verfährt wie üblich: Das System bootet.
Statt eines monolithischen Kernels kann auch ein Kernel mit einer initrd-Ramdisk per Netzwerk geladen werden. Der Rest des Bootvorganges geht dann auch wie üblich.
Boot-BIOS #
Es gibt vier verschiedene Verfahren, die hier benutzt werden:
- RPL ist ein Protokoll von Novell, das mit IPX-Paketen arbeitet und für uns Linuxer völlig ungeeignet ist. Leider habe ich z.B. einen Rechner, der nur dieses Verfahren beherrscht.
- PXE ist ein Standard- der von Intel ins Leben gerufen wurde und der (angeblich) von allen neueren Mainboards / Netzwerkkarten automatisch unterstützt wird. PXE kann normalerweise nicht direkt einen Kernel booten, sondern lädt erstmal einen bootloader (z.B. pxelinux oder bpbatch)
- etherboot ist ein etwas älteres Open Source-Projekt, das mit eigenen Netzwerkkartentreibern arbeitet. Es wird ein Boot-ROM erzeugt, das dann irgendwie in den Rechner gelangen muss. Dies kann durch einen EPROM-Baustein oder auch durch eine Diskette erfolgen. Es lädt direkt einen Linux-Kernel (oder evtl. auch erstmal GRUB als Bootloader)
- netboot ist ein etwas neueres Open Source-Projekt, das im Grunde genauso wie etherboot arbeitet. Es kann jedoch sog. Packetdriver oder NDIS-Treiber einbinden, die normalerweise von den Herstellern für DOS/Windows mit der Netzwerkkarte mitgeliefert werden. Dadurch ist es etwas zukunftsträchtiger.
Der Kernel (oder Bootloader) für etherboot/netboot muss speziell gekennzeichnet sein. D.h. netboot kann nicht den "2nd level bootloader" pxelinux laden und PXE-Karten können keine netboot-Kernel (ohne Bootloader) laden. Also kristallisiert sich letztlich die Frage PXE oder netboot heraus. Allerdings muss man bei einem vorhandenen Client oft "nehmen, was kommt", da PXE in neueren Rechnern oft bereits fertig ist und netboot/etherboot manchmal Probleme mit bestimmten Netzwerkkarten haben wird, aber andererseits PXE nicht "nachrüstbar" bzw. von Diskette zu starten ist.
Boot-Images #
Was lädt denn so ein Boot-ROM nun? Und welches Format hat das? Schön wäre eine Lösung, die sowohl PXE als auch netboot verstehen kann. Da PXE zwingend einen Bootloader braucht (z.B. pxelinux, ein Teil des syslinux-Projektes, bpbatch, ein halbkommerzielles Projekt), habe ich mich auf die Suche nach einem Bootloader gemacht, der von beiden Systemen geladen werden kann.
Der einzige, der das kann, ist GRUB. Diese Lösung hat gegenüber allen anderen (z.B. direkt einen Kernel laden oder gar eine "normale" Bootdisk) insbesondere den Vorteil, daß auf dem Client nichts (aber auch gar nichts) zu konfiguriert werden braucht, wenn einmal ein netboot (bzw. PXE) läuft, das die Netzwerkkarte erkennt. Jegliche Konfiguration, Menüs mit mehreren Kernels, Kernel-Austausch, etc. sind alle zentral am Server vorzunehmen. :-)
Da ich keinen PXE-Rechner zur Verfügung habe, habe ich ohne Bootloader nur mit netboot experimentiert. Dabei kann man mittels eines kleinen Programmes aus einem normalen Linux-Kernel eine "tagged" Kernel-Datei machen, die von netboot sofort erkannt wird.
netzwerkfähiger Bootloader GRUB #
GRUB ist nicht nur generell ein sehr leistungsfähiger LILO-Konkurrent, sondern auch Netzwerk-boot-fähig.
GRUB für netboot/PXE erzeugen #
Leider sind die Images, die für netboot bzw. pxe "getagged" sind, im normalen Debian-Paket nicht enthalten. :-( Also habe ich mir von ftp://alpha.gnu.org/gnu/grub das aktuelle Source-Paket geholt, ausgepackt, kurz netboot/README.netboot gelesen und mit ./configure --enable-diskless --enable-ns8390 und make all übersetzt.
Den Netzwerkkartentreiber (ns8390) will GRUB zwar mit angegeben haben, aber soviel ich verstanden habe, braucht man den nur, wenn man den Rechner mit GRUB bootet und dann einen Kernel vom Netz holen will. Wir booten aber mit netboot, welches die Netzwerkkarte initialisiert und dann GRUB vom Netz nachlädt. GRUB benutzt (AFAIK?) dann den bereits bestehenden Treiber für alles weitere. Wer es doch so machen will, sollte wissen, dass GRUB im Prinzip die etherboot-Treiber enthält.
Danach kopiere ich die Datei stage2/nbgrub (bzw. stage2/pxegrub für PXE-Clients) in mein tftpd-Verzeichnis.
konfigurieren #
GRUB wird über eine Datei konfiguriert, deren Namen der DHCP-Server durch eine Spezial-Option übergeben hat (siehe unten). Diese Datei hat den gleichen Aufbau wie eine normale GRUB-Konfigurationsdatei, also z.B. so:
# NBGRUB-Konfiguration default 0 timeout 1
title normales Booten vom Netzwerk kernel /tftpboot/kernel.bin ide=nodma initrd /tftpboot/initrd.bin
title Debian-Installation kernel /tftpboot/install-linux.bin kernel /tftpboot/install-root.bin
Besonderheiten beim Kernelbau #
Der Kernel und die initrd müssen alles enthalten, was Linux braucht, um die Netzwerkkarte einzurichten, per DHCP zu konfigurieren und dann per NFS ein neues root-Filesystem zu laden. Hierzu evtl. später mehr... -- ThomasBayen
Einrichtung des Servers #
Der Server muss für den eigentlichen Bootvorgang als DHCP- und TFTP-Server dienen. Dann muss er per NFS ein root-Filesystem freigeben.
DHCP / Bootp #
Eine normale NetzKonfigMitDHCP wird aufgesetzt. Darin wird eine neue Option definiert (1x) und dann für die zu bootenden Clients jeweils ein besonder Eintrag gemacht:
# Option 150 wird speziell von nbgrub ausgewertet: option grub-configfile code 150 = text;
host clientname { fixed-address 192.168.201.128; hardware ethernet 00:12:34:45:67:89; allow bootp; server-name "192.168.1.1"; filename "/tftpboot/nbgrub"; option grub-configfile "(nd)/tftpboot/nbgrub.conf"; option routers 192.168.201.1; option domain-name-servers 192.168.201.1; option domain-name "intranet"; }
TFTP #
Solange man beim Standard-Verzeichnis /tftpboot für die Freigabe bleibt, braucht man nur das Debian-Paket tftpd zu installieren und fertig.
Installation eines normalen Debian-Systems via Netzwerk #
Eigentlich wäre es ja nett, wenn man neue Rechner direkt übers Netz installieren könnte. Natürlich gibt es dafür auch Installations-CDs und Disketten, aber erstens hat nicht jeder Rechner ein CD-Laufwerk, zweitens ist das Hantieren mit mehreren Disketten umständlich und altmodisch und drittens wollte ich das einfach mal probiert haben. :-) Das wir uns nicht falsch verstehen: Ich spreche von einer ganz normalen Installation auf die Festplatte des "Clients". Die "Installation" eines Diskless-Clients ist natürlich gar nicht nötig.
Unter http://www.debian.org/releases/stable/i386/ch-install-methods.en.html#s-install-tftp steht, was Debian zu dem Thema sagt. Leider bin ich hierbei das erste Mal von der Debian-Dokumentation enttäuscht worden. Dort wird auf
http://www.debian.org/releases/stable/i386/ch-appendix.en.html#s-file-descs
verwiesen. Dort gibt es eine Datei tftpboot.img, mit der ich jedoch gar nichts anfangen konnte. Laut Anleitung ist sie nicht für PXE geeignet, laut meiner Tests aber auch nicht für netboot. Wenn man sie als Kernel lädt, funktioniert sie auch wie ein Kernel, startet aber keine passende RAM-Disk zur Debian-Installation, sondern lädt einfach /dev/hda1 als root.
Dennoch habe ich nach einigen Versuchen folgendes erreicht: Die Dateien
linux.bin (Kernel) root.bin (initrd-Ramdisk)
von obiger Seite habe ich in mein tftpboot-Verzeichnis kopiert. Welchen "flavour" man dabei nimmt, ist Geschmackssache. Für unser Vorhaben sinnvoll dürfte compact (Kernel 2.2) oder bf2.4 (Kernel 2.4) sein. Dann gibt man auf der Kommandozeile von GRUB folgendes an:
kernel /tftpboot/linux.bin flavor=bf2.4 initrd /tftpboot/root.bin boot
und schwuppdiwupp startet die Installation. Natürlich können diese Befehle auch in die GRUB-Konfigurationsdatei aufgenommen werden (wie oben im Beispiel). Die Angabe von "flavor" ist nötig, wenn man einen anderen als den Standard-Kernel (also z.B. compact oder bf2.4) installiert hat.
Da das gesamte Installationssystem in der Ramdisk ist, muss kein NFS-Server zur Verfügung stehen. Im weiteren Verlauf muss nun noch darauf geachtet werden, dass eine Installation vom Netz per FTP/HTTP gewählt wird.
-- ThomasBayen
Links #
- http://www.naos.co.nz/papers/diskless/index1.html - sehr gute Einführung in die Theorie
- http://www.linux-mag.com/2002-10/netbooting_01.html - guter Artikel im "Linux Mag"
- http://www.kegel.com/linux/pxe.html - Erklärung zu PXE und interessante Link-Liste
- http://www.bpbatch.org/docs/linux.html - bpbatch-Homepage
- http://www.gnu.org/manual/grub-0.92/html_mono/grub.html - GRUB Dokumentation
- http://www.ltsp.org/documentation/pxe.howto.html - Man kann etherboot auch per PXE booten...