182 votes

Comment voir quels drapeaux -march=native va activer ?

Je compile mon application C++ avec GCC 4.3. Au lieu de sélectionner manuellement les drapeaux d'optimisation, j'utilise la méthode suivante -march=native qui, en théorie, devrait ajouter tous les drapeaux d'optimisation applicables au matériel sur lequel je compile. Mais comment puis-je vérifier les drapeaux qu'il utilise réellement ?

167voto

thkala Points 36148

Vous pouvez utiliser le -Q --help=target options :

gcc -march=native -Q --help=target ...

El -v peut également être utile.

Vous pouvez consulter la documentation sur le --help option aquí .

13 votes

Je vais suggérer que c'est sous-optimal. La sortie de --help=target n'affiche pas les informations de cache du CPU, dont les méthodes listées par elias et 42n4 ci-dessous. Plus précisément, avec gcc 4.9.2 sur un Phenom, la sortie inclut ceci : --param l1-cache-size=64 --param l1-cache-line-size=64 --param l2-cache-size=512

0 votes

@DanielSantos : sur mon système, ces paramètres s'affichent avec la balise -v mais dans le cadre de l'option cc1 ligne de commande...

0 votes

Pas parfait. sur gcc version 5.4.0 (Buildroot 2017.05-rc2-00016-gc7eaf50-dirty) il provoquera l'erreur en retour : Messages de l'assembleur : Error : unknown architecture native Error : unrecognized option -march=native. Donc, il faut perdre l'option -march=native et cela fonctionnera partout en suivant : gcc -Q --help=target .

133voto

elias Points 209

Pour voir les drapeaux de la ligne de commande, utilisez :

gcc -march=native -E -v - </dev/null 2>&1 | grep cc1

Si vous voulez voir les définitions du compilateur/précompilateur définies par certains paramètres, faites ceci :

echo | gcc -dM -E - -march=native

3 votes

Cette réponse mérite autant de votes positifs que la réponse acceptée, notamment parce qu'elle énumère les éléments suivants native équivaut réellement à.

4 votes

Donc, si je veux faire une compilation native croisée, je dois fournir au compilateur les définitions ET les arguments ? ou les arguments sont-ils suffisants ?

28voto

42n4 Points 440

Il devrait être ( -### est similaire à -v ) :

echo | gcc -### -E - -march=native 

Pour montrer les "vrais" drapeaux natifs pour gcc.

Vous pouvez les faire apparaître plus "clairement" avec une commande :

gcc -### -E - -march=native 2>&1 | sed -r '/cc1/!d;s/(")|(^.* - )//g'

et vous pouvez vous débarrasser des drapeaux avec -mno-* avec :

gcc -### -E - -march=native 2>&1 | sed -r '/cc1/!d;s/(")|(^.* - )|( -mno-[^\ ]+)//g'

13voto

Mark Lakata Points 3458

Si vous voulez savoir comment mettre en place une compilation croisée non native, j'ai trouvé cette page utile :

Sur la machine cible,

% gcc -march=native -Q --help=target | grep march
-march=                               core-avx-i

Puis utilisez ceci sur la machine de construction :

% gcc -march=core-avx-i ...

0 votes

Cela ne comprendra pas tous les drapeaux, malheureusement.

0 votes

@BaptisteWicht Y a-t-il des drapeaux que -march=native inclura que -march=core-avx-i n'inclurait pas, dans ce cas, ou quels drapeaux ? Merci.

3 votes

@rogerdpack Sur cet ordinateur (sandybridge), march=sandybridge n'active pas AVX (je ne sais pas pourquoi) alors que march=native le fait. Une autre différence importante est que les tailles de cache ne sont extraites qu'avec march=native.

8voto

Daniel Santos Points 766

Je vais apporter mon grain de sel à cette question et suggérer une extension légèrement plus verbeuse de la réponse d'Elias. A partir de gcc 4.6, l'exécution de gcc -march=native -v -E - < /dev/null émet une quantité croissante de spam sous la forme de messages superflus. -mno-* drapeaux. Ce qui suit va les supprimer :

gcc -march=native -v -E - < /dev/null 2>&1 | grep cc1 | perl -pe 's/ -mno-\S+//g; s/^.* - //g;'

Cependant, je n'ai vérifié l'exactitude de ceci que sur deux CPU différents (un Intel Core2 et un AMD Phenom), donc je suggère d'exécuter également le script suivant pour être sûr que tous ces -mno-* peuvent être dépouillés en toute sécurité.

2021 EDIT : Il existe en effet des machines où -march=native utilise un -march valeur, mais doit désactiver certaines ISA (Instruction Set Architecture) implicites avec -mno-* .

#!/bin/bash

gcc_cmd="gcc"

# Optionally supply path to gcc as first argument
if (($#)); then
    gcc_cmd="$1"
fi

with_mno=$(
    "${gcc_cmd}" -march=native -mtune=native -v -E - < /dev/null 2>&1 |
    grep cc1 |
    perl -pe 's/^.* - //g;'
)
without_mno=$(echo "${with_mno}" | perl -pe 's/ -mno-\S+//g;')

"${gcc_cmd}" ${with_mno}    -dM -E - < /dev/null > /tmp/gcctest.a.$$
"${gcc_cmd}" ${without_mno} -dM -E - < /dev/null > /tmp/gcctest.b.$$

if diff -u /tmp/gcctest.{a,b}.$$; then
    echo "Safe to strip -mno-* options."
else
    echo
    echo "WARNING! Some -mno-* options are needed!"
    exit 1
fi

rm /tmp/gcctest.{a,b}.$$

Je n'ai pas trouvé de différence entre gcc -march=native -v -E - < /dev/null y gcc -march=native -### -E - < /dev/null à part certains paramètres qui sont cités - et les paramètres qui ne contiennent pas de caractères spéciaux, donc je ne suis pas sûr dans quelles circonstances cela fait une réelle différence.

Enfin, notez que --march=native a été introduit dans gcc 4.2, avant quoi il s'agissait simplement d'un argument non reconnu.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X