Jádro systému Linux

xobsivac at fi.muni.cz

You cannot use a computer WITHOUT compiling the OS kernel with your own hands.

– The Linux Kernel HOWTO


Obsah

Linuxové jádro
Číslování verzí
Kde to roste
Proč kompilovat jádro
Co je třeba mít v systému
Kompilace jádra snadno a rychle
Instalace jádra
Kde si o tom přečíst

Linuxové jádro

Jádro operačního systému je základní část operačního systému, která ovládá zdroje a poskytuje služby dalším částem OS a uživatelským programům (memory management, interrupts handling, task scheduling, dispatching, intertask communication, virtual file system, network interface etc.).

Historii linuxového jádra začal počátkem 90. let tehdy zhruba dvacetiletý Linus Torvalds studující na Helsinské univerzitě informatiku. Je notoricky známé, že si chtěl napsat vlastní UNIX, po vzoru Minixu, běžící na PC i386. V jednom z prvních e-mailů, kde je Linux (tehdy ho ovšem chtěl pojmenovat Freax) zmíněn, napsal: It is NOT protable (uses 386 task switching etc), and it probably never will support anything other than AT-harddisks, as that's all I have :-(. Linus se rozhodl šířit Linux pod licencí GNU GPL, což jistě podpořilo ochotu dalších lidí na něm spolupracovat.

První stabilní verze 1.0 z roku 1994 podporovala sítě TCP/IP, SCSI zařízení. Tarball měl < 1 MB. Mimo jiné vylepšení správy paměti, vlákna na úrovni jádra a podpora modulů vedla k povýšení na verzi 2.0 a nabobtnání zdrojáků na téměř 5 MB. Bylo to v roce 1996, stejně jako zrození Tuxe. Počátkem roku 1999 byla oficiálně vypuštěna verze 2.2 (více než 12 MB) s vylepšenou podporou CD-ROM a výměnných médií, frame bufferem, širší paletou FS. Verze 2.4 (20 MB) zvládá 64 GB operační paměti na intelovské architektuře, žurnálovací FS, modernější firewall (iptables).

Na dveře klepe jádro 2.6, jehož zabalené zdrojové kódy mají více než 30 MB, a v už tak těžkém batohu přináší navíc:


Podrobně viz [6].

Moduly (Loadable kernel modules), všemi milované, umožňují dynamicky zavádět další funkce do jádra, které nejsou staticky slinkované v době kompilace. Jako modul je vhodné mít funkce, které nejsou potřeba při "běžném běhu systému" nebo třeba obsahují nový kód, který chceme testovat.

Stojí to režii, která je zanedbatelná v porovnání s výhodami: lze je kompilovat samostatně, umožňují snadnější odhalování chyb než kód jádra, úspora paměti, rychl. start systému. Jakmile je modul nahrán, stává se regulérní součástí jádra a může tedy shodit jádro stejně jako jakýkoliv jiný kód jádra nebo ovladače.

O automatické nahrávání modulů se stará démon kerneld, ručně můžete pomocí příkazu modprobe (případně agresivnější, bez kontroly verze a závislosti insmod). Module-HOWTO.


Číslování verzí

– formát tří čísel x.y.z

Speciálně jsou označeny testovací verze nadcházející stabilní verze např. 2.6.0-test1.

čísla posledních verzí: stabilní 2.4.22 a ve fázi mrazení vývojové 2.6.0-test6 (i když by někteří raději viděli 3.0)


Kde to roste

The Linux Kernel Archives
http://www.kernel.org/ (vhodnější je využít mirror, např. http://www.linux.cz/ :)

Tzv. Vanilla verze jádra (přímo od Linuse), na ni "pasuje" většina patchů.

Patchované od distributora, obvykle v balíčku kernel-source (bezpečnost, podpora více FS, ovladače apod.). Víhoda balíčků je, že by za vás měli pohlídat závislosti. Debian nepachuje.


Proč kompilovat jádro

Aby bylo přizpůsobené systému.


Co je třeba mít v systému

Zdrojové texty, cc resp. gcc, as (překladač asembleru z balíčku binutils), as86 (dev86, příp. bin86), make (make), glibc + hlavičkové soubory (ne knihovny :) glibc-devel, glibc-kernheaders, tar, bzip2, pro konfiguraci pomocí menuconfig ncurses (i ncurses-devel), patch. Více a přesně pro vaši verzi jádra v Documentation/Changes. Připravený skript (scripts/ver_linux) vypisuje verze programů, které máte nainstalované.


Obsah stromu se zdrojovými texty

Zdrojový stromu

© 2001 Richard West

linux/Documentation – dokumentace
linux/arch – podadresáře pro každou podporovanou architekturu
linux/drivers – největší část kódu jádra – ovladače
linux/fs – virtuální FS, podadresáře pro každý FS
linux/initversion banner vypisovaný při startu systému a boot kód
linux/kernel – hmm, co by tady mohlo být?
linux/lib – "náhrady" knih. funkcí C (errno, string)
linux/mm – paging, swapping, (de)allocation, memory mapping
linux/scripts – menuconfig a další užitečné skripty (ver_linux)


Kompilace jádra snadno a rychle

  1. download, příprava

    Důvěřuj, ale prověřuj – můžete si stáhnout přímo z kernel.org soubor vase_verze.sign pro kontrolu signatury. Pokyny najdete na stránce, na kterou je v souboru uveden odkaz.

    Zdroje jádra patří do adresáře /usr/src/linux/ (lepší /usr/src/linux-verze/ a symlink). Můžete ale kompilovat v libovolném adresáři. Pokud chcete verzi z balíčku, tak lepší než upgrade je instalace, smazat starší můžete, až všechno pošlape.

    bzip2 -dc linux-verze.tar.bz2 | tar xvf -
    ln -s linux-verze linux
    

    Na zdrojáky před kompilací pust'te make mrproper. Rozhodně pokud jste před chvilkou nakopírovali novější release na původní, co byl v /usr/src/linux/, nebo máte zdrojáky od RedHatu. Máte zálohu souboru .config?

    Také je vhodná doba aplikovat patche. A už oficiální mezi jednotlivými release (připravené pro Vanilla verze) nebo jiné záplaty (FS, crypto, driver, Alan Cox "test bed for Linus' kernels" patches aj.). Doporučuje se použít příkaz patch -p1 –-dry-run, další možnost je skript scripts/patch-kernel.

    bzip2 -cd ../patch-verze.bz2 | patch -p1

    Četl jsem: Eg, patch-2.4.8-pre2 goes on top of an unpacked 2.4.7 tarball, *not* on top of a patched 2.4.8-pre1 kernel. Ale tenhle postup se mi u 2.6.0 neosvědčil. Patche 2.6.0-testX jsem postupně aplikoval na 2.5.75, bez chybové hlášky. Čtěte příslušná README! Každopádně patch -R může v nejisté situaci pomoci.

  2. konfigurace – určení částí a funkcí, které má nové jádro obsahovat

    make [menu|x|old]config

    make config je "hardcore", make menuconfig je přehledný způsob (ncurses), make xconfig obdoba vyžadující Xka + Tcl/Tk, pozor, vše se nastavuje pomocí myši ;), make oldconfig je vhodné pro upgrade s nastavením pouze nových voleb. Konfigurace je v souboru .config, je vhodné ho proto zálohovat.

    Význam důležitých konfiguračních voleb viz [4].

    Pokud hodláte překládat vícekrát stejnou verzi jádra s různou konfigurací, je rozumné vyplnit parametr EXTRAVERSION v souboru Makefile (na něco srozumitelného např. -noipv6).

  3. kopilace

    make dep clean
    make bzImage

    kontrola závislostí; úklid; vytvoření obrazu jádra; pokud máte jádro schopné provozu bez modulů, můžete zadat make bzdisk (místo make bzImage), čímž vytvoříte disketu, ze které můžete zkusit nabootovat. I když je to ve spoustě dokumentace jinak, ušetřit čas u novějších verzí můžete vynecháním clean. A dokonce bude zbytečné i make dep; o čem se časem budou dělat referáty?

  4. v případě, že chcete (chcete!) moduly, pak také

    make modules

    Ovladač IDE jako modul není rozumné, chcete-li z disku bootovat, narozdíl od floppy. Pokud máte některé ovladače v modulech, ale potřebujete je už při startu jádra, máte možnost použít initrd – ram disk, do kterého si při startu jádro může šáhnout. Obraz ramdisku vytvoříte příkazem mkinitrd.

Nyní je vhodné státi se rootem (práva pro zápis do /lib/modules/.

make modules_install

Verzí zdrojáku je dost, překlad je složitá záležitost, kroky se mohou mírně lišit. Podívejte se na konkrétní postup do dokumentace dodané s vaší verzí! Aspoň to README ;-)


Instalace jádra

Jste si jisti, že vaše "záchranná disketa" neslouží jako podšálek? Odvážní mohou pokračovat i tak...

Istalací se rozumí přinucení vašeho zavaděče (angl. boot loader, nikoli boot manager; několik v abecedním pořadí: Grub, Gujin, LILO, Nuni) nalézt při startu systému to správné místo na disku, kde máte požadované jádro, které má zavést do paměti. BTW existuje projekt http://www.linuxbios.org/ – zavaděč postavený na kernelu, ale to už se nám to moc zamotává :-)

cp arch/i386/boot/bzImage /boot/vmlinuz-kernel.version.number
cp System.map /boot/System.map-k.v.n

System.map – info about the entry points of the functions you compiled into your kernel and de-bug information. Mapuje adresy v jádře na symboly, vy se bez něj obejdete, ale některé programy (ps, top, klogd) ho potřebují, aby mohly vypisovat některé informace o běžících procesech.

Upravit linky na nové soubory:

/usr/src/linux # soft link linux -> linux-stara-verze-jadra
/usr/src/System.map

Na tomto místě se doporučuje přidat ve svém boot loaderu položku se starším kernelem (/etc/lilo.conf), jistota je jistota. Pro naše počítače, kde je i systém druhé skupiny, ještě položku pro boot jejich jádra!

/sbin/lilo

Občas bývá zapomenuto. Pak je pravděpodobné, že nabootujete starou verzi jádra nebo nenabootujete vůbec, bylo-li už na disku přepsáno. To se pak člověk může divit, že se nové jádro chová stejně jako staré :) Zavaděče jdoucí na FS (Grub) tento problém neznají.

Restart s troškou napětí. Kontrola, co je vlastně nastartováno (viz nástroje), pár bezesných nocí, jestli to pořád funguje, a je to. Rescue disc (bzdisk nebo mkbootdisk).

make rpm; make clean

Obdoba make rpm na Debianu – nástroj make-kpkg, který postup kompilace automatizuje a výsledkem kompilace je deb balíček. Ten obsahuje jádro, moduly, System.map... a navic ví, kam co do systému příjde.

Výhody: soubory jadra jsou podchyceny balíčkovacím systémem a tedy lépe spravovatelné; méně práce při nutnosti instalovat jádro na víc mašin.


Parametry jádra při startu

root= určení zařízení, na kterém se nachází / (kořen FS). Např. /dev/nfs, /dev/ram

ro (mount / readonly) narozdíl od rw

nfsroot= adresace / na NFS

mem= vnucení jádru kolik si má myslet, že máme paměti

acpi= pouze hodnota off pro vypnutí subsystému ACPI

debug vypisovat zprávy jádra pomocí printk(), nejen na disk, ale i na konzoli

quiet něco jako opak předchozího, minimum hlášení, např. nic o detekci hw při bootu

init= co má jádro spustit jako init program, např. /bin/sh

panic= kolik vteřin čekat před restartem systému, pokud došlo k interní chybě jádra

vga= nastavení obrazovky (ještě před startem jádra), např. 80x50 nebo ask (Documentation/svga.txt)

A další jako parametry ovlivňující ramdisk, např. noinitrd, chování sběrnice PCI, Video Frame Buffer, SCSI zařízení, viz BootPrompt-HOWTO.


Nástroje

uname(1) – print system information

dmesg(8) – print or control the kernel ring buffer

lsmod(8) – list loaded modules

(co nahrát hned při bootu: /etc/modules.autoload, /etc/modules v Debianu)


Kde si o tom přečíst

[1] The Linux Kernel HOWTO

http://www.linux.cz/linuxdoc/HOWTO/Kernel-HOWTO/index.html
(a další z http://www.linux.cz/linuxdoc/HOWTO/HOWTO-INDEX/os.html#OSKERNEL)

[2] Index of Documentation for People Interested in Writing and/or Understanding the Linux Kernel

http://jungla.dit.upm.es/~jmseyas/linux/kernel/hackers-docs.html

[3] Poznámky k jádru Linux 2.4 (Kamil Toman, Martin Mačok)

http://artax.karlin.mff.cuni.cz/~toman/linux/
make bzImage, bootování, start jádra, init thread, syst. volání; synchronizace (kernelové semafory, spinlocky); _detailně_ (pro čtení nutná alespoň minimální znalost assembleru a architektury x86).

[4] Seriál Triky pro začátečníky (Leoš Literák)

http://www.root.cz/clanek/538

[5] Překládáme jádro (Zdeněk Pytela)

http://www.linuxzone.cz/index.phtml?ids=9&idc=442

[6] Seriál Báječný svět Linuxu 2.6 (překlad článku Josepha Praneviche od Davida Häringa)

http://www.linuxzone.cz/index.phtml?ids=10&idc=782

[7–999] Nestačí?

http://directory.google.com/Top/Computers/Software/Operating_Systems/Linux/Kernel/

Referát do předmětu PB090 UNIX – seminář ze správy systému, 1. 10. 2003