8.26.1. Installation de GCC
Tout d'abord, corrigez un problème cassant libasan.a
lors de la construction de ce paquet
avec Glibc-2.34 ou supérieur :
sed -e '/static.*SIGSTKSZ/d' \
-e 's/return kAltStackSize/return SIGSTKSZ * 4/' \
-i libsanitizer/sanitizer_common/sanitizer_posix_libcdep.cpp
Si vous construisez sur x86_64, changez le nom du répertoire par
défaut des bibliothèques 64 bits en « lib » :
case $(uname -m) in
x86_64)
sed -e '/m64=/s/lib64/lib/' \
-i.orig gcc/config/i386/t-linux64
;;
esac
La documentation de GCC recommande de construire GCC dans un
répertoire de construction dédié :
mkdir -v build
cd build
Préparez la compilation de GCC :
../configure --prefix=/usr \
LD=ld \
--enable-languages=c,c++ \
--disable-multilib \
--disable-bootstrap \
--with-system-zlib
Remarquez que pour d'autres langages de programmation, il existe
des prérequis qui ne sont pas encore disponibles. Consultez la
page GCC du livre BLFS pour des instructions sur la manière de
construire tous les langages pris en charge par GCC.
Voici la signification des nouveaux paramètres de
configuration :
-
LD=ld
-
Ce paramètre permet de s'assurer que le script configure
utilise le ld installé par binutils, construit plus tôt dans
ce chapitre, au lieu de la version compilée de manière
croisée qui serait autrement utilisée.
-
--with-system-zlib
-
Ce paramètre dit à GCC de se lier à la copie de la
bibliothèque zlib installée sur le système, plutôt qu'à sa
propre copie interne.
Compilez le paquet :
make
Important
Dans cette section, la suite de tests de GCC est considérée comme
importante, mais elle prend beaucoup de temps. Les novices sont
encouragés à ne pas l'ignorer. La durée des tests peut être
significativement réduite en ajoutant -jx à la commande make
ci-dessous, où x est le nombre de cœurs sur votre système.
Un ensemble de tests dans la suite de tests de GCC est connu pour
utiliser toute la pile par défaut, c'est pourquoi vous devez
augmenter la taille de la pile avant de lancer les tests :
ulimit -s 32768
Testez les résultats en tant qu'utilisateur non privilégié, mais ne
vous arrêtez pas aux erreurs :
chown -Rv tester .
su tester -c "PATH=$PATH make -k check"
Pour recevoir un résumé des résultats de la suite de tests,
lancez :
../contrib/test_summary
Pour n'avoir que les résumés, redirigez la sortie vers
grep -A7 Summ
.
Vous pouvez comparer les résultats avec ceux situés dans https://www.linuxfromscratch.org/lfs/build-logs/11.1/
et https://gcc.gnu.org/ml/gcc-testresults/.
Huit tests liés à l'analyseur sont connus pour échouer.
Un test nommé asan_test.C
est connu
pour échouer.
Dans libstdc++, un test nommé 49745.cc
est connu pour échouer parce que les
dépendances des en-têtes de glibc ont changé.
Dans libstdc++, un test numpunct et six tests liés à get_time sont
connus pour échouer. Tout cela est du aux définitions des
paramètres régionaux dans glibc qui ont changées, mais libstdc++ ne
prend pas encore en charge ces changements.
Quelques échecs inattendus sont parfois inévitables. Les
développeurs de GCC connaissent généralement ces problèmes, mais
ils ne les ont pas encore résolus. Sauf si les résultats des tests
sont très différents de ceux sur l'adresse ci-dessus, vous pouvez
poursuivre en toute sécurité.
Installez le paquet et supprimez un répertoire inutile :
make install
rm -rf /usr/lib/gcc/$(gcc -dumpmachine)/11.2.0/include-fixed/bits/
Le répertoire de construction de GCC appartient maintenant à
tester
et la propriété du
répertoire des en-têtes installé (et son contenu) sera incorrecte.
Transférez la propriété à l'utilisateur et au groupe root
:
chown -v -R root:root \
/usr/lib/gcc/*linux-gnu/11.2.0/include{,-fixed}
Créez un lien symbolique requis par le FHS
pour des raisons « historiques ».
ln -svr /usr/bin/cpp /usr/lib
Ajoutez un lien symbolique de compatibilité pour permettre la
compilation de programmes avec l'optimisation à l'édition des liens
(LTO) :
ln -sfv ../../libexec/gcc/$(gcc -dumpmachine)/11.2.0/liblto_plugin.so \
/usr/lib/bfd-plugins/
Maintenant que notre chaîne d'outils est en place, il est important
de s'assurer à nouveau que la compilation et l'édition de liens
fonctionneront comme prévu. Vous devez alors effectuer plusieurs
contrôles d'intégrité :
echo 'int main(){}' > dummy.c
cc dummy.c -v -Wl,--verbose &> dummy.log
readelf -l a.out | grep ': /lib'
Il ne devrait pas y avoir d'erreur et la sortie de la dernière
commande sera (avec des différences spécifiques aux plateformes
dans le nom de l'éditeur de liens) :
[Requesting program interpreter: /lib64/ld-linux-x86-64.so.2]
Maintenant, assurez-vous que nous utilisons les bons fichiers de
démarrage :
grep -o '/usr/lib.*/crt[1in].*succeeded' dummy.log
La sortie de la dernière commande devrait être :
/usr/lib/gcc/x86_64-pc-linux-gnu/11.2.0/../../../../lib/crt1.o succeeded
/usr/lib/gcc/x86_64-pc-linux-gnu/11.2.0/../../../../lib/crti.o succeeded
/usr/lib/gcc/x86_64-pc-linux-gnu/11.2.0/../../../../lib/crtn.o succeeded
Selon l'architecture de votre machine, le message ci-dessus peut
légèrement différer. La différence porte sur le nom du répertoire
après /usr/lib/gcc
. Il est important
de vérifier que gcc a
trouvé les trois fichiers crt*.o
sous
le répertoire /usr/lib
.
Vérifiez que le compilateur cherche les bons fichiers
d'en-têtes :
grep -B4 '^ /usr/include' dummy.log
Cette commande devrait afficher la sortie suivante :
#include <...> search starts here:
/usr/lib/gcc/x86_64-pc-linux-gnu/11.2.0/include
/usr/local/include
/usr/lib/gcc/x86_64-pc-linux-gnu/11.2.0/include-fixed
/usr/include
À nouveau, le répertoire nommé selon votre triplet cible peut être
différent de celui ci-dessus, selon l'architecture de votre
système.
Puis, vérifiez que le nouvel éditeur de liens est utilisé avec les
bons chemins de recherche :
grep 'SEARCH.*/usr/lib' dummy.log |sed 's|; |\n|g'
Les références vers des emplacements qui contiennent
« -linux-gnu » doivent être ignorées, sinon la sortie de
la dernière commande doit être :
SEARCH_DIR("/usr/x86_64-pc-linux-gnu/lib64")
SEARCH_DIR("/usr/local/lib64")
SEARCH_DIR("/lib64")
SEARCH_DIR("/usr/lib64")
SEARCH_DIR("/usr/x86_64-pc-linux-gnu/lib")
SEARCH_DIR("/usr/local/lib")
SEARCH_DIR("/lib")
SEARCH_DIR("/usr/lib");
Un système 32 bits peut voir quelques répertoires
différemment. Par exemple, voici la sortie d'une machine
i686 :
SEARCH_DIR("/usr/i686-pc-linux-gnu/lib32")
SEARCH_DIR("/usr/local/lib32")
SEARCH_DIR("/lib32")
SEARCH_DIR("/usr/lib32")
SEARCH_DIR("/usr/i686-pc-linux-gnu/lib")
SEARCH_DIR("/usr/local/lib")
SEARCH_DIR("/lib")
SEARCH_DIR("/usr/lib");
Ensuite, assurez-vous que nous utilisons la bonne libc :
grep "/lib.*/libc.so.6 " dummy.log
La sortie de la dernière commande devrait être :
attempt to open /usr/lib/libc.so.6 succeeded
Assurez-vous que GCC utilise le bon éditeur de liens
dynamiques :
grep found dummy.log
La sortie de la dernière commande devrait être (avec des
différences spécifiques aux plateformes dans le nom de l'éditeur de
liens) :
found ld-linux-x86-64.so.2 at /usr/lib/ld-linux-x86-64.so.2
Si la sortie ne ressemble pas à celle montrée ci-dessus ou qu'elle
n'apparaît pas du tout, c'est que quelque chose ne va vraiment pas.
Enquêtez et retracez les étapes pour trouver le problème et
corrigez-le. Tout problème devra être résolu avant de continuer le
processus.
Une fois que tout fonctionne correctement, nettoyez les fichiers
tests :
rm -v dummy.c a.out dummy.log
Enfin, déplacez un fichier mal placé :
mkdir -pv /usr/share/gdb/auto-load/usr/lib
mv -v /usr/lib/*gdb.py /usr/share/gdb/auto-load/usr/lib