• # Réponse : oui

    Posté par . En réponse au message Linux from scratch pour Raspeberry: préparation depuis un PC. Évalué à 4.

    Voici mes notes. Elles datent d’environ un an, donc il y aura peut-être des mises à jour à faire. C’est très synthétique (ce n’était pas destiné à publication) : il faut donc avoir un très bon niveau pour pouvoir s’en servir.

    Ça utilise Gentoo par contre, si tu connais pas, peut-être vaut-il mieux l’utiliser avant sur un poste ordinaire : de toute façon mes notes utilisent Gentoo comme système de build, avec une partition btrfs (un subvolume faisant office d’image virtuelle du système : on versionne le système et on met à jour le diff seulement sur la carte, c’est vraiment le top pour travailler).

    C’est un gros boulot. J’avais fini par abandonner mon but initial. Mais il y a déjà de quoi faire avec mes notes. À toi d’adapter en fonction de tes besoins. Je livre tel quel, j’espère que cela te sera utile ou à d’autres même si ça n’utilise pas LFS. Bon courage !

    Je crois savoir que sous Debian il existe aussi un système de compilation croisée.

    Introduction
    ============
     Il s’agit d’utiliser la carte comme un serveur pour de
     l’auto‐hébergement. On exploitera les fonctionnalités les
     plus avancées des systèmes Linux et les dernières
     innovations (btrfs, systemd, kexec, gentoo, etc.). Par
     exemple btrfs conjugué à kexec autoriseront des mises à jour
     fiables du système sur la carte SD. Gentoo permettra de
     configurer le système afin de veiller à des performances
     optimales, avec la mise en place d’une compilation croisée
     et d’une distribution binaire des paquets.
     Le serveur web sera léger (lighttpd à priori) et fera appel
     à FCGI/C++, via une technologie "semi‐statique" : les pages
     html seront servies statiquement, mais il sera possible de
     les modifier via l’exposition d’une API HTTP get/post
     adéquate. La modification des pages html fera appel au *copy‐
     on‐write* et au renommage atomique. En guise de démonstration
     technologique, on créera un blog simple. On pourra aussi
     réutiliser, moyennant quelques menues adaptations, les
     scripts dash/make qui me permettent de tenir à jour ma
     galerie d’images & vidéos.
    Pré-requis
    ----------
     Achat pour ~50 ,ドル livraison comprise, sur [materiel.net](http://materiel.net) :
     — Raspberry Pi B+ ;
     — alimentation 1,2 A (dont ~700 mA pour la carte) ;
     — carte microSDHC classe 4 Kingston 4 GB ;
     — cable ethernet court, sans blindage.
     On peut vérifier avec une raspbian que le tout fonctionne
     correctement, et on peut récupérer les options du noyau dans
     `/proc/config.gz`, utiles si l’on ne les a pas déjà.
     Connaissances requises :
     — administration d’une gentoo, niveau intermédiaire ;
     — administration de serveurs, web & mail essentiellement.
     — systemd, niveau débutant ;
     — base en développement C ;
     — chaîne de compilation (config/econf, make/emake, install).
     Documentation :
     — [guide](http://wiki.gentoo.org/wiki/Raspberry_Pi) gentoo sur la raspberry ;
     — [guide](https://www.gentoo.org/proj/en/base/embedded/handbook/?part=1) gentoo sur les systèmes embarqués ;
     — page `man ebuild` de gentoo ;
     — pages `man systemd`.
    Compilation croisée
    ===================
     On utilisera une variable de confort
     `ARM="armv6j-hardfloat-linux-gnueabi"`
     à placer dans son `~/.$(basename $SHELL)rc`.
     Faire :
     `sudo emerge sys-devel/crossdev
     sudo crossdev -S -P \-j2 -oO /usr/local/portage \
     --target $ARM`
     Si on vous le demande, il vous faudra convertir certains
     fichiers de `/etc/portage` en répertoire. Toutes les options
     du type `‐jN` peuvent être adaptées, ici et par la suite, avec
     N le nombre de cœurs de vos processeurs — c’est la célèbre
     option de make, passée telle quelle. On va combler un manque
     de crossdev :
     `sudo cp /usr/bin/$ARM-emerge /usr/bin/$ARM-ebuild`
     puis éditer le fichier nouvellement créé en remplaçant toute
     référence à emerge par ebuild et en supprimant l’argument
     `--root-deps=rdeps`.
     Il est temps de configurer & compiler un système de base :
     `sudo ln -nsf \
     /usr/portage/profiles/default/linux/arm/13.0/armv6j \
     /usr/$ARM/etc/portage/make.profile`
     puis éditer le fichier `/usr/$ARM/etc/portage/make.conf` :
     `CFLAGS="-O2 -pipe -fomit-frame-pointer
     -march=armv6j -mfpu=vfp -mfloat-abi=hard"
     USE_PYTHON="2.7"
     PYTHON_TARGETS="python2_7"
     MAKEOPTS="-j2"
     PORTAGE_NICENESS=19
     PORTAGE_TMPDIR=/tmp/
     USE="${ARCH} -pam
     systemd python2 minimal
     -acl -kmod -firmware-loader -cracklib
     -nls -cramfs"`
     Notez bien que si je prends l’option d’un répertoire de
     travail dans `/tmp`, c’est pour que la compilation se déroule
     dans un tmpfs — c’est le cas de `/tmp` chez moi — sans pour
     autant interférer avec le répertoire de travail du portage
     principal — dans `/var/tmp` chez moi. Enfin :
     `sudo $ARM-emerge systemd btrfs-progs dash`
     Cela devrait nous mener à quelques erreurs de compilation.
     Voyons comment les résoudre.
    À propos des problèmes de compilation
    -------------------------------------
     Il faut commencer par consulter les logs laissés par
     portage. Par exemple à partir de
     `/tmp/portage/sys-apps/shadow-4.2.1/temp/build.log`
     on atteint
     `[..]/sys-apps/shadow-4.2.1/work/shadow-4.2.1/config.log`
     et ce dernier mène au script `configure:14778` dans le même
     répertoire.
     Il faut donc débrayer emerge et passer en manuel pour que
     portage puisse compiler les paquets qui posent problème.
     Pour ce faire on utilisera ebuild : je renvoie à sa
     documentation. Pour toute la section nous supposerons être
     root. En utilisant le fichier `.ebuild`, dans `/usr/portage` et
     correspondant au paquet à installer (attention à la version
     du paquet!), les commandes utiles sont :
     `$ARM-ebuild xxx.ebuild prepare
     $ARM-ebuild xxx.ebuild configure
     $ARM-ebuild xxx.ebuild compile
     $ARM-ebuild xxx.ebuild install
     $ARM-ebuild xxx.ebuild qmerge
     $ARM-ebuild xxx.ebuild package
     $ARM-ebuild xxx.ebuild clean`
     Par exemple avec shadow, on prépare le répertoire de
     travail, et ensuite on modifie le script configure aux
     alentours de la ligne 14 778. En effet on réalise que le
     problème vient de ce que le script a besoin de compiler et
     d’exécuter un petit programme à la volée pour vérifier si
     certaines données sont en 32 bits. Dans un contexte de
     compilation croisée, c’est pas cool ! Ceci dit, on sait que
     la raspberry est 32 bits. Il nous suffit donc de modifier le
     script en conséquence pour qu’il n’ait pas à faire son test,
     mais qu’il exécute les actions nécessaires en admettant un
     résultat de type 32 bits.
     En ce qui concerne btrfs, il sera probablement nécessaire de
     compiler le paquet acl avant, puis de suivre la procédure
     manuelle, pour faire un petit tour vers le Makefile afin de
     désactiver la compilation de l’inutile documentation, qui
     nécessite asciidoc, dont les dépendances sont trop lourdes.
     Parfois les problèmes sont plus profonds, et il peut être
     nécessaire de bloquer la version la plus récente d’un paquet
     se trouvant la plupart du temps dans `~arm`. Ce fut le cas
     pour `libgpg‐error‐1.13`.
     Pour clucene, réclamé plus tard par dovecot compilé avec la
     recherche plein texte, il faut désactiver le test de
     `snprintf`, après vérification manuelle sur la raspberry. Mais
     c’est insuffisant : une erreur de programmation subsiste
     lorsque les espaces de nom C++ ne sont pas disponibles. En
     effet le dévelopeur a bêtement utilisé un espace de nom
     directement plutôt qu’une macro ad‐hoc correspondante. Ceci
     dit, finalement, j’ai activé les espaces de nom directement,
     après vérification manuelle du test CMake sur la raspberry
     bien sûr, en modifiant directement le fichier cache de
     CMake. Ce fut nécessaire pour ne pas avoir de conflits au
     moment du lien.
     Rebelotte pour Dovecot. Toujours la même chose : l’étape
     configure réclame la compilation et l’exécution de
     programmes à la volée. Il faut modifier le script `configure`
     pour court‐circuiter les tests de epoll et inotify dont on
     veillera à l’activation dans le noyau. Il en est de même
     pour `fallocate` de posix, et des `size_t` non signés, après
     vérification manuelle. Le nombre de bits supportés par
     `gmtime` est 32, les `time_t` sont signés, `mmap` accepte les
     `write`, un obscur truc à propos de `fd` passe le test (premier
     de la boucle) sans problème, idem pour `vsnprintf`, et
     quelques test sur les listes à taille variable d’arguments.
    Noyau
    =====
     `USE="-symlink" sudo emerge \
     sys-kernel/raspberrypi-sources \
     sys-boot/raspberrypi-mkimage`
     J’ai installé la version des sources noyau qui correspond à
     mon système principal, suffisament récente pour btrfs — à
     l’heure où j’écris ce texte, c’est 3.14 —, et j’ai rendu
     permanent la suppression du USE symlink dans un fichier de
     `/etc/portage/package.use`. Puis dans le dossier des sources
     du noyau :
     `sudo make ARCH=arm CROSS_COMPILE=$ARM- make -j2
     sudo mkdir /usr/$ARM/boot
     sudo imagetool-uncompressed.py --force
     arch/arm/boot/Image /usr/$ARM/boot/kernel.img`
     J’utilise un noyau monolitique avec un [.config](http://TODO|le `.config` de mon noyau actuel) issu d’une
     raspbian (`/proc/config.gz`) et modifié pour être le plus
     minimaliste possible. Il faut veiller à certaines [options](Doivent être activées les deux options menuconfig qui concernent kexec ainsi que CONFIG_ATGS, pour plus tard, et les dépendances systemd pour le noyau : AUTOFS4_FS ok, BLK_DEV_BSG ok, CGROUPS ok, DEVTMPFS ok, DMIID n/a, EPOLL ok, FANOTIFY ok, FHANDLE ok, INOTIFY_USER ok, IPV6 ok, NET ok, NET_NS ok, PROC_FS ok, SECCOMP ok, SIGNALFD ok, SYSFS ok, TIMERFD ok, TMPFS_XATTR ok, !IDE ok, !SYSFS_DEPRECATED ok, !SYSFS_DEPRECATED_V2 ok, !GRKERNSEC_PROC ok, !FW_LOADER_USER_HELPER ok).
    Système
    =======
     Rechercher dans les [dépots](http://distfiles.gentoo.org/releases/arm/autobuilds/current-stage3-armv6j_hardfp/) gentoo l’archive stage3 la plus
     récente, et noter son `url` :
     `wget $url
     wget \
     http://distfiles.gentoo.org/snapshots/portage-latest.tar.bz2
     sudo btrfs subvolume create root-work
     sudo tar xjpf stage3-armv6j_hardfp-xxx.tar.bz2 -C root-work/
     sudo tar xjpf portage-latest.tar.bz2 -C root-work/usr/ `<- TODO image miroir de /usr/$ARM/usr/bla
     Tenter un mount --bind`
     sudo $ARM-emerge --root root-work --unmerge udev
     PKGDIR=/usr/$ARM/packages sudo $ARM-emerge \
     systemd btrfs-progs dash --root root-work --usepkgonly`
     Il faut utiliser les fichiers fournis sur la partition de
     boot de la raspbian, car ceux du paquet gentoo ad‐hoc ne
     sont pas bons. La procédure consiste à lancer :
     `sudo parted bla-raspbian.img unit b print`
     Regarder le début de la partition fat16, et s’en servir
     comme `offset` :
     `mkdir boot
     sudo mount -o offset=$offset bla-raspbian.img boot
     sudo cp boot/* /usr/$ARM/boot
     sudo umount boot
     rmdir boot`
     Puis éditer le fichier `/usr/$ARM/boot/cmdline.txt`, sur une
     seule ligne :
     `console=tty1
     root=/dev/mmcblk0p2
     rootfstype=btrfs
     elevator=noop
     rootwait
     init=/usr/lib/systemd/systemd
     quiet
     ro
     rootflags=compress=lzo`
     puis le fichier `/usr/$ARM/boot/config.txt` pour les options :
     `hdmi_safe=1
     gpu_mem=16`
     Enfin, `root-work/etc/fstab` doit contenir :
     `/dev/mmcblk0p1 /boot vfat noauto,noatime 1 2
     /dev/mmcblk0p2 / btrfs noatime,compress=lzo 0 1
     /dev/mmcblk0p2 /mnt btrfs noatime,subvol=/,compress=lzo 0 0`
     Ne pas oublier de créer le lien :
     `sudo ln -s /proc/self/mounts root‐work/etc/mtab`
     Puis éditer le fichier `root-work/etc/systemd/journald.conf` :
     `Storage=volatile
     RuntimeMaxUse=10M`
     Activer le synchronisation de temps : <- TODO: ne fonctionne pas à cause d’une entrée /dev absente
     `sudo systemctl enable --root root-work \
     systemd-timesyncd.service`
     Bien noter qu’il faut copier l’unité correspondante du côté
     de `/etc` et y supprimer la ligne `PrivateTmp=yes`, et penser à
     créer le fichier `/var/lib/systemd/clock` avec le bon
     propriétaire (voir la section sur la création d’un système
     de fichier mixte ro‐rw). Pour localiser la zone horaire :
     `sudo ln -sf \
     /usr/share/zoneinfo/Europe/Paris root-work/etc/localtime`
     Le système d’init se contentera d’un démarrage simplifié :
     `sudo systemctl set-default basic.target --root root-work`
    Réseau & OpenSSH
    ----------------
     L’interface réseau est reconnue comme étant le très
     classique eth0. Il faut créer l’unité `static‐eth0.service`
     dans `root‐work/etc/systemd/system/network.target.wants` :
     `[Unit]
     Description=Static ethernet connection
     Before=network.target
     BindsTo=sys-subsystem-net-devices-eth0.device
     After=sys-subsystem-net-devices-eth0.device
     [Service]
     Type=oneshot
     RemainAfterExit=yes
     KillMode=none
     ExecStart=/bin/ifconfig eth0 192.168.0.2 \
     broadcast 192.168.0.255 netmask 255.255.255.0 up
     ExecStart=/bin/route add default gw 192.168.0.254`
     On n’oublie pas les DNS :
     `sudo cp -L /etc/resolv.conf root-work/etc/`
     On doit mettre en place le serveur ssh. Pour cela ajouter un
     lien :
     `sudo systemctl --root root-work enable sshd.socket`
     Editer le fichier de configuration
     `root-work/etc/ssh/sshd_config`
     pour supprimer, ou commenter, la ligne :
     `UsePAM yes
     AcceptEnv LANG LC_*`
     Puis faire (première commande le cas échéant) :
     `sudo ssh-keygen <- TODO: doit être fait pour chaque image fournie/téléchargée
     sudo mkdir root-work/root/.ssh
     sudo chmod 700 root-work/root/.ssh
     sudo cp \
     /root/.ssh/id_rsa.pub root-work/root/.ssh/authorized_keys
     sudo mount --bind root-work/root/etc/ssh /etc/ssh
     sudo ssh-keygen -A
     sudo umount /etc/ssh`
    Préparation de la carte SD
    --------------------------
     Pour finir on prépare le snapshot à placer sur la carte SD,
     pour cela, créer une partition FAT16 commençant à 4096kB et
     ayant l’étiquette lba, et une seconde pour le fichier racine
     en btrfs. Attention à bien spécifier les bons fichiers bloc
     pour les deux première commandes, car elles sont tout
     particulièrement dangereuses :
     `sudo mkfs.fat -F16 /dev/sdX1
     sudo mkfs.btrfs /dev/sdX2
     sudo mount /dev/sdX1 /mnt
     sudo cp /usr/$ARM/boot/* /mnt
     sudo umount /mnt
     sudo btrfs subvolume snapshot -r root-work root-xxx
     sudo mount /dev/sdX2 /mnt
     sudo btrfs send raspberry/root-xxx | sudo btrfs receive /mnt
     sudo btrfs subvolume set-default \
     $(sudo btrfs inspect-internal rootid /mnt/root-xxx) /mnt
     sudo umount /mnt`
    Finaliser l’installation
    ========================
     Si tout se passe bien, les étapes précédentes auront permis
     de créer un système fonctionnel avec lequel la raspberry
     peut démarrer, se connecter au réseau local, et ouvrir un
     serveur ssh. Une connection ssh depuis le compte root permet
     de valider l’opération.
     On pourra continuer le travail en supposant que la raspberry
     est allumée et accessible via le nom d’hôte éponyme. Pour ce
     faire, écrire dans le fichier /etc/hosts :
     `192.168.0.2 raspberry`
    Kexec & mise-à-jour à distance
    ------------------------------
     Nous allons installer kexec pour montrer comment on peut
     faire évoluer le système :
     `sudo $ARM-emerge kexec-tools
     PKGDIR=/usr/$ARM/packages sudo $ARM-emerge kexec-tools \
     --root root-work --usepkgonly
     sudo btrfs subvolume snapshot -r root-work root-xxx-r1
     sudo btrfs send -p root-xxx root-xxx-r1 -f incr.img
     sudo scp incr.img raspberry:/tmp
     sudo ssh raspberry
     mount -o subvol=/ /dev/mmcblk0p2 /mnt
     btrfs receive -f /tmp/incr.img /mnt
     btrfs subvolume set-default \
     $(btrfs inspect-internal rootid /mnt/root-xxx-r1) /mnt
     umount /mnt
     systemctl reboot`
     Ce qui devrait logiquement fermer la connexion ssh. Attendre
     quelques secondes, puis relancer :
     `sudo ssh raspberry
     mount -o subvol=/ /dev/mmcblk0p2 /mnt
     btrfs subvolume delete /mnt/root-xxx
     umount /mnt
     kexec -v`
     La dernière commande devrait être ok : on a réalisé une mise
     à jour à distance de notre raspberry !
     Pourquoi kexec ? Et bien, si un nouveau noyau tombe dans un
     `kernel panic` et que l’option
     `menuconfig->kernel hacking->panic timeout`
     est réglée à 10 (par exemple), alors qu’il est lancé avec
     kexec, la carte redémarrera automatiquement sur l’ancien
     noyau. Elle est pas belle la vie ? Voyons voir, compilons un
     nouveau noyau, selon la procédure décrite précédemment.
     Puis :
     `sudo scp arch/arm/boot/zImage raspberry:/tmp
     sudo ssh raspberry
     kexec -l /tmp/zImage --atags --command-line="$(cat /proc/cmdline)"
     kexec -e` <- TODO c’est pas du propre !
    Rendre fonctionnel l’ensemble
    -----------------------------
     Pour corriger les erreurs qui subsistent, il suffit d’ouvrir
     le journal systemd. Par exemple, mon installation montre que
     des groupes et des utilisateurs qui sont nécessaires au bon
     fonctionnement de systemd, etc. n’ont pas été créés. J’ai
     corrigé cela en ajoutant les lignes nécessaires aux fichiers
     `/etc/passwd` & `/etc/group`, directement piquées de mon système
     principal.
     C’est aussi le journal qui permet de connaître les
     répertoires qui doivent être accessibles en écriture pour la
     section suivante.
    Système de fichier mixte ro–rw
    ------------------------------
     Btrfs permet d’obtenir un système de fichier qui utilise
     deux blocs mémoire sources, dont un est en lecture seule. On
     va donc procéder à la création d’un fichier image qui
     contiendra un système de fichiers en lecture seule, et d’un
     bloc situé en mémoire vive accessible en écriture, et qui
     sera le *copy‐on‐write* du fichier image. On pourra ainsi
     limiter les écritures sur la carte SD, afin de la préserver.
     Pour initier la procédure, toujours sur la raspberry, avec
     la variable shell `rep` l’ensemble des répertoires qui doivent
     être en écriture, en suivant la convention de nommage de
     systemd :
     `dd if=/dev/zero of=/mnt/live bs=128M count=1
     mkfs.btrfs /mnt/live
     mount -o loop /mnt/live /media
     btrfs subvolume create /media/0
     for r in $rep;do mkdir /media/0/$r;done
     btrfs property set /media/0 ro true
     ln -s 0 /media/cur
     umount /media`
     Et sur l’ordinateur principal, toujours dans le répertoire
     où se trouve `root‐work` le répertoire destiné à être la
     racine du système de fichier de la raspberry :
     `sudo mkdir root-work/live`
     Éditer les fichiers `root-work/etc/fstab` :
     `/mnt/live /mnt btrfs loop,noatime 0 0`
     ensuite `root-work/usr/local/sbin/live.start` :
     `#!/bin/dash
     current=$(readlink /live/cur)
     other=$((1 - ${current}))
     if [ -d /live/${other} ]
     then
     /bin/umount /live
     /sbin/btrfstune -fS0 /mnt/live
     /bin/mount /live
     /sbin/btrfs subvolume delete /live/${other}
     /bin/umount /live
     /sbin/btrfstune -S1 /mnt/live
     /bin/mount /live
     fi
     btrfs device add -Kf /dev/ram0 /live
     mount -o rw,remount /live
     btrfs subvolume snapshot /live/${current} /live/${other}
     ln -snf ${other} /live/cur`
     et enfin `root-work/usr/local/sbin/live.stop` :
     `#!/bin/dash
     [ -f /live/volatile ] && exit 0
     current=$(readlink /live/cur)
     other=$((1 - ${current}))
     btrfs property set /live/${current} ro true
     btrfs send -p /live/${other} /live/${current} -f /tmp/live.incr
     umount /live
     btrfstune -fS0 /mnt/live
     mount /live
     btrfs receive -f /tmp/live.incr /live \
     && ln -nsf ${current} /live/cur.tmp \
     && mv -T /live/cur.tmp /live/cur \
     && btrfs subvolume delete /live/${other}
     umount /live \
     && btrfstune -S1 /mnt/live \
     && btrfs filesystem sync /mnt`
     Puis rendre les deux scripts exécutables :
     `chmod u+x root-work/usr/local/sbin/live.st*`
     Ils seront appelés par une unité systemd chargée de gérer ce
     montage d’un type un peu particulier dans `/live`, on écrit
     donc `root-work/etc/systemd/system/live.service` :
     `[Unit]
     DefaultDependencies=false
     RequiresMountsFor=/mnt /tmp /live
     [Service]
     Type=oneshot
     RemainAfterExit=true
     ExecStart=/usr/local/sbin/live.start
     ExecStop=/usr/local/sbin/live.stop`
     ainsi que `root-work/etc/systemd/system/live-pre.service` :
     `[Unit]
     DefaultDependencies=false
     RequiresMountsFor=/mnt
     Before=live.mount
     [Service]
     Type=oneshot
     SuccessExitStatus=1
     ExecStart=/sbin/btrfstune -S1 /mnt/live`
     et pour finir `root-work/etc/systemd/system/live.mount` :
     `[Unit]
     DefaultDependencies=false
     RequiresMountsFor=/mnt
     Requires=live-pre.service
     After=live-pre.service
     [Mount]
     What=/mnt/live
     Where=/live
     Options=loop,noatime`
     Il faut noter une fonctionnalité qui permet de désactiver le
     script d’arrêt, qui est particulièrement long lorsqu’on 
     teste, en plaçant un fichier vide `/live/volatile`, auquel cas
     on perd la persistance des données.
     On va ensuite créer des unités systemd de type `.mount` afin
     de gérer tous les répertoires qui doivent être accessibles
     en écriture. Elles devront dépendre du service qui vient
     d’être écrit. Il faut rendre accessible en écriture un
     certain nombre de répertoires, par exemple `/var/log` &
     `/var/lib/systemd`. Ce qui donne, par exemple, une unité
     dans `/etc/systemd/system/local‐fs.target.wants` de nom fixé
     `var‐log.mount` :
     `[Unit]
     DefaultDependencies=false
     Requires=live.service
     After=live.service
     Before=systemd-tmpfiles-setup.service
     [Mount]
     What=/live/cur/var-log
     Where=/var/log
     Options=bind`
     Et ainsi de suite, en veillant à bien respecter le nommage
     des unités comme systemd le réclame (voir la documentation).
     Il faut aussi créer les dossiers voulus sur la raspberry :
     si cela n’est pas déjà fait, enlever momentanément la
     propriété `ro` du volume concerné par `/live/cur`, puis y créer
     les dossiers tout en respectant, encore une fois, le schéma
     de nommage.
    Logiciels tiers
    ===============
    Serveurs
    --------
     Pour installer le serveur, on ajoute les USE nécessaires :
     `sieve managesieve lucene
     -threads
     -mysql -sqlite -gdbm`
     dans `/usr/$ARM/etc/portage/make.conf`, puis :
     `sudo $ARM-emerge \
     fetchmail ssmtp dovecot lighttpd`
     Pour les erreurs de compilation, se reporter à la section
     correspondante. Pour l’installation :
     `PKGDIR=/usr/$ARM/packages sudo $ARM-emerge \
     fetchmail ssmtp dovecot lighttpd \
     --root root-work --usepkgonly`
     Il faut là encore mettre en place les bons utilisateurs dans
     `/etc/passwd` & `/etc/group`. Il faut aussi les bons dossiers
     accessibles en écriture. Par exemple, sur la raspberry :
     `mkdir /var/log/lighttpd
     chown lighttpd:lighttpd /var/log/lighttpd
     rm /live/volatile
     systemctl stop live.mount`
     Ainsi le script d’arrêt est bien appelé dans sa version
     complète, comme cela peut prendre un moment on peut se
     renseigner sur son avancement :
     `systemctl status live.mount`
     puis remonter le tout :
     `systemctl start live.service
     systemctl start var-log.mount
     systemctl start var-lib-systemd.mount`
     avec l’avantage d’être toujours en volatile, si c’était le
     cas, car le fichier ad‐hoc a uniquement été supprimé du
     système de fichier en ram.
     Le cache de compression de lighttpd se trouve dans
     `/var/cache/lighttpd`, mis en tmpfs (`size=512M`) dans
     `/etc/fstab` en oubliant pas de placer un `RequiresMountsFor`
     adéquat pour l’unité lighttpd, ce qui aurait déjà dû être
     fait pour le `/var/log/lighttpd`.
    Outils
    ------
     Gnuplot et Imagemagick sont de la partie. Le premier sans
     readline mais avec gd (png), le second avec cxx et jpeg.
     TODO : Des erreurs de compilation apparaissent, sans
     surprise. Pour Gnuplot, c’est la création de fichiers d’aide
     qui bloque. Ce ne devrait pas être un problème. Pour
     Imagemagick, il faut creuser du côté de la libtool.
    Perspectives
    ============
     Penser à la possibilité d’ajouter une petite batterie,
     typiquement ce que j’ai sur mon XZ‐1. Il existe des
     convertisseurs 3,7 à 5 V DC. Cela permettrait une extinction
     propre de la machine au débranchement de l’alimentation,
     avec un peu de travail sur l’électronique. On pourrait
     relâcher ainsi la contrainte d’écriture sur la carte SD.
    TODO: redémarrer en cas de fail du net ou du ssh.
    TODO: faire du kexec et améliorer le noyau (unité systemd nécessaire, notamment pour veiller à la bonne gestion du live.service).
    TODO: kexec en changeant la cmdline pour démarrer sur un nouveau snapshot !!! pb avec fstab pas à jour?
    TODO: Documentation/cmdline-partition, pour indiquer la table de partitions sur la ligne de commande, sans compter l’utilisation d’un device static.
    TODO: utile de compléter le fichier /etc/shadow ?
    TODO: comment se passe la gestion des fichiers /var/log et/ou /var/lib/systemd
    TODO: voir si le premier umount avec -f dans live.stop accélère la vitesse du démontage (qui peut être forcé sans problème)
    TODO: SIGSTOP&SIGCONT pour pouvoir garder lighttpd sur le fil lorsqu’on doit effectuer un live.stop&live.start pour les dossiers du serveur.
    TODO: check pagesize of the raspberry
    TODO: ssh-keygen doit pouvoir être relancé pour chaque image.