Démarrage du système
La personnalisation du processus de démarrage (boot) implique de comprendre comment les scripts de démarrage sont appelés. Ce chapitre décrit également les problèmes communs que vous pourrez rencontrer au cours des différentes étapes du processus de démarrage ainsi que des techniques de récupération. Enfin nous focaliserons notre attention sur le chargement du disque virtuel en mémoire initrd au démarrage du système. Cela nous permettra de décider quand la création d'un disque virtuel en mémoire est nécessaire.
État :
Sommaire
Pré-requis
- Niveau LPIC 1
Personnaliser le processus de Boot
Présentation d'init
Afin d'éviter que les processus lancés par les utilisateurs interfèrent avec le noyau, deux espaces de mémoire distinct ont été définis : l'espace mémoire du noyau et l'espace mémoire utilisateur. Le processus init est le premier programme lancé dans l'espace utilisateur.
init est donc le processus père de tous les processus. Le fichier de configuration de init est : /etc/inittab
Les niveaux d'exécution (runlevels)
Les niveaux d'exécution déterminent quels processus doivent fonctionner ensemble. Tous les processus peuvent être démarrés ou stoppés à un niveau d'exécution donné par un script (appelé script init ou script rc) dans /etc/rc.d/init.d (RedHat).
Liste des scripts RC sur un système standard :
anacron halt kudzu ntpd rusersd syslog ypxfrd apmd identd lpd portmap rwalld vncserver atd ipchains netfs radvd rwhod xfs autofs iptables network random sendmail xinetd crond kdcrotate nfs rawdevices single ypbind functions keytable nfslock rhnsd snmpd yppasswdd gpm killall nscd rstatd sshd ypserv
La sélection d'un processus qui doit être lancé ou stoppé dans un niveau d'exécution donné est effectuée par la création de liens symboliques dans le répertoire /etc/rc.d/rcN.d/ ou N est le niveau d'exécution.
Exemple 1 : Sélectionner le processus httpd pour le niveau d'exécution 3
ln -s /etc/rc.d/init.d/httpd /etc/rc.d/rc3.d/S85httpd
Information : Le nom du lien est le même que celui du processus mais précédé par un S pour start et un nombre représentant l'ordre d'exécution.
Exemple 2 : Stopper le processus httpd pour le niveau d'exécution 3
rm /etc/rc.d/rc3.d/S85httpd ln -s /etc/rc.d/init.d/httpd /etc/rc.d/rc3.d/K15httpd
Cette fois, le nom de la ligne débute avec un K pour Kill pour s'assurer que le processus est arrêté lors du passage d'un niveau d'exécution a l'autre.
Lancement des scripts locaux
Nous voulons lancer un script a un niveau d'exécution donné . Notre script sera appelé printtotty10 et affichera simplement le message donné en argument a /dev/tty10.
/bin/printotty10
# !/bin/bash echo $1 > /dev/tty10
Une possibilité d'avoir le script lancé a un niveau d'exécution spécifique est d'ajouter une ligne dans /etc/inittab comme :
pr10:3:once:/bin/printtotty10 “Printtotty a été lancé dans inittab”
Ce n'est pas toujours la meilleurs solution. Que se passe t-il si vous devez lancer beaucoup de scripts ? Le fichier inittab sera illisible.
- Nous allons écrire un rc-script personnalisé. Nous suivons la méthode pour appeler le même nom que l'outil que nous voulons lancer.
/etc/rc.d/init.d/printtotty10
# !/bin/sh # chkconfig: 345 85 15 # description: Cette ligne est necessaire au fonctionnement de chkconfig... \ # Ce script affiche un message sur /dev/tty10 # Tout d'abord, recuperons des fonctions pre-definies comme echo_success() ./etc/rc.d/init.d/functions start() { echo -n "lancement de printtotty10" /bin/printtotty10 "printtotty10 a ete lance a partir d un script rc" echo_success echo } stop() { echo -n "Arret de custom-rc" /bin/printtotty10 "Le script personnalise a ete arrete" echo_success echo } case "$1" in start) start;; stop) stop;; esac exit 0
Le script printtotty10 peut être lancé au moment du démarrage (boot) en plaçant la commande dans /etc/rc.d/rc.local. Le script rc.local est le dernier script rc a être lancé.
Information: lorsque vous voulez configurer un serveur Linux comme un routeur, il est possible d'activer l'ip-forwarding au moment du démarrage par l'ajout de la ligne suivante dans rc.local :
echo 1 > /proc/sys/net/ipv4/ip_forward
Cependant il est mieux d'utiliser le mécanisme de sysctl pour activer l'ip-forwarding chaque fois que le réseau est démarré. On le fait en ajoutant la ligne suivante dans /etc/sysctl.conf :
net.ipv4.ip_forward = 1
2. La récupération du système
Quand un système se bloque et ne parvient pas à redémarrer, il est nécessaire de modifier le processus de démarrage normal. Cette section décrit quelques solutions correspondant à des problèmes qui peuvent se produire aux étapes suivantes du processus de démarrage.
Étape de démarrage |
Type d'erreur |
Solution suggérée| |
INIT |
Systeme de fichier Racine corrompu ou une erreur dans le fichier /etc/fstab |
Utiliser le prompt en utilisateur root |
Échec de chargement d'un module du Noyau ou d'un script RC |
Redéfinition d'INIT ( voire page 23) ou utiliser un runlevel alternatif |
|
KERNEL |
Panique du Noyau (Kernel panic) |
(Voire page 24) |
Erreur d'initialisation materiel ( souvent avec des anciens Noyaux sur les dernières carte mères) |
Mettre le paramètre approprié sur le chargeur de démarrage - acpi=off. (p.27) |
|
BOOT LOADER |
Non installé ou endommagé |
Utiliser un disque de secours ou un disque de démarrage (voire p.24) |
Redéfinition de l'étape d'init
Cela est nécessaire si le processus de démarrage échoue à cause d'un script d'initialisation défectueux. Une fois que le noyau a réussit à trouver le système de fichiers racine, il va essayer de lancer /sbin/init. Mais le noyau peut être chargé d'exécuter un shell à la place qui nous permettra d'avoir accès au système avant que les services soit démarrés.
Au démarrage de GRUB ou LILO, a l'invite de commande ajouter le paramètre de noyau suivants:
init=/bin/bash
A la fin de l'étape de démarrage du Noyau vous devrez obtenir un invite de commande bash. Un accès en lecture / écriture sur le système de fichier racine est obtenu de la manières suivante :
mount /proc mount -o remount,rw /
Erreur a la fin de l'étape du Noyau
. Si le Noyau ne peut monter le système de fichier racine il affichera le message suivant :
Kernel panic: VFS: Unable to mount root fs on 03:05
Le nombre 03 est le numéro majeur pour le premier contrôleur IDE, et 05 est la 5eme partition sur le disque. Le problème est que le Noyau et ses modules d'accès au disque sont absent .
Nous devons pour démarrer le système utiliser une méthode alternative. La prochaine difficulté consiste à créer un initrd personnalisé et de l'utiliser pour le processus de démarrage normal.
Question: Dans le cas précèdent le disque n'est pas un disque SCSI , qu'est ce qui pourrait avoir causé le problème ?
. Si le mauvais disque racine est transmis au Noyau par le chargeur de démarrage ( LILO ou GRUB ) l'étape INIT ne pourra pas démarrer depuis /sbin/init qui sera manquant.
Kernel Panic: No init found. Try passing init= option to kernel
Encore une fois nous avons besoin de démarrer le système en utilisant une méthode différente, puis modifier le fichier de configuration du chargeur de démarrage (pour dire au Noyau d'utiliser un autre disque comme système de fichier racine), et redémarrage.
Dans les deux scénarios ci-dessus, il n'est pas toujours nécessaire d'utiliser une disquette de secours. En fait, c'est souvent la cas d'un démarrage avec un Noyau configuré proprement. Mais qu'advient-il si l'on ne dispose pas de l'option? Que ce passe t-il si le chargeur de démarrage a été configuré avec le mauvais Noyau n'utilisant pas l'initrd ou essayant de monter le mauvais système de fichier racine ?
Ce qui nous amène a la cause la plus proche possible du problème de démarrage.
Chargeur de démarrage mal configuré
A cette étape nous avons besoin d'utiliser une méthode de secours pour démarrer le système.
Utilisation d'un disque de secours
Nous savons déjà via le LPI 101 que tout CD de distribution Linux peut être utiliser pour démarrer un système en mode secours. L'avantage de ces CD c'est qu'ils fonctionnent sur tout type de système Linux.
Le processus de secours peut être ventilés dans les étapes suivantes :
1. Démarrer depuis le CD et trouver les options appropriées ( souvent appelé rescue ou boot an existing system( démarrer sur un système existant)).
2. Dans la plupart des cas le disque racine pour un système existant est automatiquement détecté et monté dans un sous répertoire du périphérique racine (en RAM).
3. Si le point de montage est appelé /system il peut devenir le système de fichier racine par notre shell courant en tapant :
chroot /system
4. A cette étape l'ensemble du système est disponible et le chargeur de démarrage peut être réparé.
Quand un chargeur de démarrage est mal configuré on peut utiliser un chargeur de démarrage de remplacement (sur une disquette ou un CD). Ce chargeur de démarrage va charger le Noyau avec lequel est configuré l'utilisation du périphérique racine sur le disque.
Cette méthode est appelé un disque de démarrage et peut être utilisé pour récupérer un système spécifique.
Disque de démarrage personnalisé 1:
Nous avons besoins d'une disquette avec une image du Noyau Linux qui peut démarrer, et cette image doit savoir ou trouver le périphérique racine sur le disque.
En supposant que nous utilisons une disquette DOS préformaté, la commande suivante va créer une disquette bootable avec lequel nous lancerons une image du Noyau Linux :
dd if=/boot/vmlinuz of=/dev/fd0
Ensuite, rdev est utilisé pour dire au Noyau ou est le périphérique racine. La commande doit être lancer sur le système que nous tenons a protéger et la disquette avec le noyau doit etre dans le lecteur.
rdev /dev/fd0 /dev/hda2
Disque de démarrage personnalisé 2:
Le paquet syslinux installe un binaire appelé syslinux qui peut être utilisé pour créer une disquette bootable. La procédure (prise dans la documentation du paquet) se présente comme ceci :
1. Faire une disquette DOS bootable. Cela peut se faire par l'option spécifique /s lors du formatage du disque en DOS, ou par le lancement de la commande SYS DOS ( cela peut se faire en vertu de DOSEMU si DOSEMU a directement accès au périphérique):
format a: /S
- ou
sys a:
2.Démarrage Linux. Copier le secteur de démarrage (boot) DOS a partir du disque dans n fichier :
dd if=/dev/fd0 of=dos.bss bs=512 count=1
3. Lancer SYSLINUX sur le disque:
syslinux /dev/fd0
4.Monter le disque et copier le secteur de démarrage DOS a partir du fichier. Le fichier *doit* avoir une extension .bss :
mount -t msdos /dev/fd0 /mnt cp dos.bss /mnt
5.Copier l'image(s) du Noyau Linux,initrd(s), etc .. dans le disque, et créer/éditer syslinux.cfg et les fichiers d'aides si vous le désirez :
Par exemple si vous avez un disque racine /dev/sda1, syslinux.cfg serait :
DEFAULT linux LABEL linux KERNEL vmlinuz APPEND initrd=initrd.img root=/dev/sda1
puis
cp /boot/vmlinuz /mnt cp /boot/initrd.img /mnt
6. Démonter le disque
umount /mnt
Informations |
Bien que SYSLINUX peut être installer sur un CD , il est recommandé d'utiliser ISOLINUX a la place ( voire p.53). |
Paramètre du Noyau par le chargeur de démarrage
load_ramdisk=n |
Si n est égale a 1 ca charge un disque virtuel, par défaut c'est 0 |
prompt_ramdisk=n |
Si n est égale a 1 on vous invite a insérer une disquette contenant un disque virtuel |
nosmp ou maxcpus=N |
Désactive ou limite le nombre de CPU (processeur) |
apm=off |
Désactive APM, parfois nécessaire pour démarrer a partir d'une carte mère non supportée |
init= |
Par défaut /sbin/init mais peut etre un shell ou processus alternatif |
root= |
Définit le périphérique racine ( peut être définit par rdev) |
mem= |
Définit une taille de RAM utilisable |
vga= |
Change le type de vidéo pour la console ( peut être définit avec rdev) |
*Le manuelle de rdev dit : L'utilitaire rdev, lorsqu'il est utilisé autrement que pour trouver un nom pour le périphérique racine actuel, est une ancienne astuce qui fonctionne en modifiant l'image du noyau à un offset avec un numéro magique. Il ne fonctionne pas sur d'autres architectures que i386. Son utilisation est fortement déconseillée. Utilisez un chargeur de démarrage comme SysLinux ou LILO .
Dépannage de LILO
Quand on installe LILO le chargeur de démarrage,/sbin/lilo,il va sauvegarder le chargeur de démarrage existant.
Par exemple si vous installez LILO sur une disquette, le chargeur de démarrage original sera sauvegarder dans /boot/boot.0200
Idem lorsqu'on change le chargeur de démarrage sur un disque IDE ou un SCSI le fichier sera appelé respectivement boot.0300 et boot.0800. Le chargeur de démarrage original peut être restauré avec :
lilo -u
Par défaut la deuxième étape de LILO est appelé /boot/boot.b et quand il est chargé avec succès il vous invite a un prompt avec boot:.
Voici les erreurs possibles lors de la phase de démarrage (extrait du README LILO)
.nothing : LILO n'est pas installé ou la partition n'est pas active .L : La première étape du chargeur de démarrage a été chargé mais pas la deuxième. .LI : La seconde étape du chargeur de démarrage a été chargé mais n'est pas valide pour être exécuter. ''This could be cause if /boot/boot.b moved and /sbin/lilo wasn't rerun'' .LIL La seconde étape du chargeur de démarrage a été exécuté, mais il ne peut pas chargé la table de description situé dans le fichier map ou la seconde étape du chargeur de démarrage a été chargé avec une addresse incorrecte. ''This could be cause if /boot/boot.b moved and /sbin/lilo wasn't rerun.'' .LIL- La table de description est corrompu ''This could be cause if /boot/map moved and /sbin/lilo wasn't rerun.'' .Scrolling 010101 errors Cela se produit lorsque le chargeur d'amorçage est situé sur un périphérique esclave
initrd personnalisé
Dans la plupart des cas un initrd personnalisé nécessite la commande mkinitrd qui déterminera les modules du Noyau nécessaire pour supporter les périphériques block et les systèmes de fichier utiliser sur le périphérique racine.
Le script Mkinitrd |
Les éléments suivants sont utilisées dans le script mkinitrd pour déterminer les informations critiques sur le périphérique racine et les systèmes de fichiers. -Le système de fichier racine : L'utilisation de "/etc/fstab" le script détermine quel système de fichier est utilisé sur le périphérique racine et le module correspondant ( par example "ext3" ou "Xfs" ). -RAID Logiciel : L'utilisation de "/etc/raidtab" , le script "Mkinitrd" en déduit le nom du Raid pour démarrer tous les disques. -Périphérique Racine LVM Depuis le périphérique racine "$rootdev" est déterminé dans "/etc/fstab", le Nombre majeur est obtenu depuis la ligne suivante : ''root_major=$(/bin/ls -l $rootdev | awk '{ print $5 }')'' Si cela correspond a un volume logique, la commande des volumes logique sont copiés dans la ram disk . Le script "mkinitrd" va transférer tous les outils et modules nécessaires a monter un système de fichier en tant que dispositif de boucle sur un répertoire temporaire. Une fois démonté, le fichier est compressé et est utilisé comme un initrd.
Syntaxes
La syntaxe de mkinitrd pour Debian et les autres distributions sont différentes.
Mkinitrd pour Debian |
Options: -d confdir Spécifie un répertoire de configuration alternatif. -k Garde le répertoire temporaire utiliser pour construire l'image. -m command Défini la commande pour créer une image initrd. -o outfile Écrit le fichier de sortie. -r root Écrit les paramètres ROOT dans mkinitrd.conf
Exemple: mkinitrd -o /boot/initrd-test-$(uname -r).img |
-
Mkinitrd pour Mandriva,RedHat,Suse/Novell |
usage: mkinitrd [--version] [-v] [-f] [--preload <module>] [--omit-scsi-modules] [--omit-raid-modules] [--omit-lvm-modules] [--with=<module>] [--image-version] [--fstab=<fstab>] [--nocompress] [--builtin=<module>] [--nopivot] <initrd-image> <kernel-version>
Exemple: mkinitrd /boot/initrd-test-2.2.5-15.img 2.2.5-15 |
Exemple
Comme exemple nous allons copier le contenu d'un initrd existant vers un nouveau initrd et changer le système de fichier d'un ext3 vers un ext2 ..
- 1.Décompresser le initrd courant
cp /boot/initrd-your-kernel-version.img /tmp/initrd.img.gz gunzip /tmp/initrd.img.gz
- 2.Monter l'initrd courant
mkdir /mnt/current mount -o loop /tmp/initrd.img /mnt/current
- 3.Estimation de la taille nécessaire pour le nouveau initrd:
df -k /mnt/current Filesystem 1K-blocks Used Available Use% Mounted on /tmp/initrd.img 317 191 126 61% /mnt/current
- 4.Créer un nouveau fichier image appelé initrd-new.img d'une taille de 161k
dd if=/dev/zero of=/tmp/initrd-new.img bs=1K count=317
- 5.Estimer le nombre d'inodes nécessaire dans l'initrd courant:
df -i /mnt/current Filesystem Inodes IUsed IFree IUse% Mounted on /tmp/initrd.img 48 33 15 69% /mnt/current
- 6.Créer un système de fichier sur le fichier /tmp/initrd-new.img avec 48 inodes:
mke2fs -F -m 0 -N 48 /tmp/initrd-new.img
- 7.Monter le fichier sur un nouveau répertoire et copié tous les fichiers de l'initrd courant vers le nouveau:
mkdir /mnt/new mount -o loop /tmp/initrd-new.img /mnt/new (cd /mnt/current/; tar cf - .) | (cd /mnt/new; tar xf -)
8.Éditer le fichier /mnt/new/linuxrc et supprimer la ligne ou est insérer le module ext3. Remplacer aussi l'option ext3 par ext2 a la commande mount. 9.Finalement, démonter le fichier /tmp/initrd-new.img puis compresser et renommer le.
gzip /tmp/initrd-new.img ; mv /tmp/initrd-new.img.gz /boot/initrdtest.img
Ou
gzip < /tmp/initrd-new.img > /boot/initrd-test.img
- 10.Créer une nouvelle entrée pour le Noyau dans /etc/lilo.conf ou /boot/grub/grub.conf informant le chargeur de démarrage d'utiliser le nouveau initrd.
Extrait grub.conf
title linux (2.4.22) root (hd0,1) kernel /vmlinuz-2.4.22 ro root=LABEL=/ initrd /initrd-2.4.22.img title broken? root (hd0,1) kernel /vmlinuz-2.4.22-1.2115.nptl ro root=LABEL=/ initrd /initrd-new.img
Extrait lilo.conf
image=/boot/vmlinuz-2.4.22-1.2115.nptl initrd=/boot/initrd-2.4.22.img read-only label=linux append=”root=LABEL=/” image=/boot/vmlinuz-2.4.22-1.2115.nptl initrd=/boot/initrd-new.img read-only label=broken? append=”root=LABEL=/”