2014-12-10 17 views
6

Wenn wir fragen, was -march=native expandiert nach, scheint das Ergebnis, wie esWarum `gcc -Q -march = corei7-avx --help = target` liegt?

$ gcc -Q -march=native --help=target | grep -E '^\s+-.*(sse|march)' 
    -march=       corei7-avx 
    -mno-sse4       [disabled] 
    -msse        [enabled] 
    -msse2       [enabled] 
    -msse2avx       [disabled] 
    -msse3       [enabled] 
    -msse4       [enabled] 
    -msse4.1       [enabled] 
    -msse4.2       [enabled] 
    -msse4a       [disabled] 
    -msse5        
    -msseregparm      [disabled] 
    -mssse3       [enabled] 

Aber wenn die Architektur direkt angegeben sein sollte, gcc fällt der SSE-Flags für native ermöglichen würde, warum?

$ gcc -Q -march=corei7-avx --help=target | grep -E '^\s+-.*sse' 
    -mno-sse4       [enabled] 
    -msse        [disabled] 
    -msse2       [disabled] 
    -msse2avx       [disabled] 
    -msse3       [disabled] 
    -msse4       [disabled] 
    -msse4.1       [disabled] 
    -msse4.2       [disabled] 
    -msse4a       [disabled] 
    -msse5        
    -msseregparm      [disabled] 
    -mssse3       [disabled] 

Compilation mit -march=corei7-avx zeigt jedoch, dass sie aktiviert sein werden.

$ echo | gcc -march=corei7-avx -dM -E - | grep -i sse 
#define __SSE4_1__ 1 
#define __SSE4_2__ 1 
#define __SSE2_MATH__ 1 
#define __SSE_MATH__ 1 
#define __SSE2__ 1 
#define __SSSE3__ 1 
#define __SSE__ 1 
#define __SSE3__ 1 
+2

Lie impliziert eine Absicht zu täuschen, was ich bezweifle, ist der Fall, mit * inkorrekt * oder ein anderes ähnliches Wort scheint angemessener. –

Antwort

3

Ich bin ein wenig zu raten, aber wie auch immer, das ist zu lang für einen Kommentar ...

Werfen Sie einen Blick auf die Ausgabe dieses Befehls:

$ echo | gcc -march=native -v -x c -c - 

Und dieses andere :

$ echo | gcc -march=corei7-avx -v -x c -c - 

der interessante Teil ist der Aufruf an die cc1 binär. Im -march=native Fall wird es durch alle Zieloptionen ersetzt, nicht nur durch das Äquivalent -march. Ich habe ein sandybridge, so in meinem Rechner gibt es:

.../cc1 -march=sandybridge -mmmx -mno-3dnow -msse -msse2 -msse3 -mssse3 \ 
     -mno-sse4a -mcx16 -msahf -mno-movbe -mno-aes -mno-sha -mpclmul \ 
     -mpopcnt -mno-abm -mno-lwp -mno-fma -mno-fma4 -mno-xop ... 

Während, wenn Sie die -march=corei7-avx oder (-march=sandybridge in meinem Fall) hinzufügen, gibt es keine dieser spezifischen Architekturoptionen.

Jetzt ist mein Fazit:

Der Ausgang des -Q --help=target sagen, ob die angegebenen Compiler-Optionen gesetzt sind, nicht, wenn Feature tatsächlich oder nicht aktiviert ist. Wie es passiert, können einige dieser Funktionen auf verschiedene Arten aktiviert oder deaktiviert werden. Beispiel: SSE kann mit -msse und auch mit -march=corei7-avx oder -march=sandybridge aktiviert werden. Aber obwohl die Angabe -march=corei7-avx SSE aktiviert, werden die -msse Optionen per se nicht festgelegt.

Auf der anderen Seite setzt -march=native viele Optionen, nicht nur die tatsächliche -march, sondern auch jede andere relevante Option, die aus dem Laufzeitsystem wie Cache-Größen abgerufen werden können.

Der richtige Weg, um zu überprüfen, ob eine bestimmte Funktion aktiviert oder deaktiviert ist, ist, wie Sie bereits bemerkt haben, das Überprüfen der vordefinierten defines.

3

Dies ist ein bekannter Fehler in GCC (39851); Es ist offen seit GCC 4.5 in 2009.