How to see which flags -march=native will activate?
Asked Answered
L

6

205

I'm compiling my C++ app using GCC 4.3. Instead of manually selecting the optimization flags I'm using -march=native, which in theory should add all optimization flags applicable to the hardware I'm compiling on. But how can I check which flags is it actually using?

Lurlenelurline answered 29/3, 2011 at 9:14 Comment(0)
S
184

You can use the -Q --help=target options:

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

The -v option may also be of use.

You can see the documentation on the --help option here.

Spates answered 29/3, 2011 at 9:24 Comment(4)
I'm going to suggest that this is suboptimal. The output of --help=target doesn't display CPU cache information, of which the methods both elias and 42n4 below have listed. Specifically, on gcc 4.9.2 on a Phenom, the output includes these: --param l1-cache-size=64 --param l1-cache-line-size=64 --param l2-cache-size=512Prankster
@DanielSantos: on my system it does display those parameters with the -v option, albeit as part of the cc1 command line...Spates
not perfect. on gcc version 5.4.0 (Buildroot 2017.05-rc2-00016-gc7eaf50-dirty) it will cause the error in return: Assembler messages: Error: unknown architecture native Error: unrecognized option -march=native. So, loose the -march=native and it will work everywhere just following: gcc -Q --help=target.Sauterne
@Oleg - That sounds like a bug in GCC 5. The issue is not present in GCC 7.Infinite
S
163

To see command-line flags, use:

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

If you want to see the compiler/precompiler defines set by certain parameters, do this:

echo | gcc -dM -E - -march=native
Sackcloth answered 20/2, 2012 at 3:30 Comment(3)
This answer deserves as many upvotes as the accepted one for, in particular, listing what native really equates to.Hildebrandt
so if i'd like to cross-native-compile, i should feed both the compiler both the defines AND the arguments? or is the arguments sufficient?Confiscatory
Pretty sure that the arguments are sufficient.Picaroon
D
29

It should be (-### is similar to -v):

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

To show the "real" native flags for gcc.

You can make them appear more "clearly" with a command:

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

and you can get rid of flags with -mno-* with:

gcc -### -E - -march=native 2>&1 | sed -r '/cc1/!d;s/(")|(^.* - )|( -mno-[^\ ]+)//g'
Debbydebee answered 23/9, 2013 at 15:26 Comment(0)
S
15

If you want to find out how to set-up a non-native cross compile, I found this useful:

On the target machine,

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

Then use this on the build machine:

% gcc -march=core-avx-i ...
Stoops answered 13/6, 2014 at 20:21 Comment(4)
This will not include all the flags unfortunately.Quixotism
@BaptisteWicht are there flags that -march=native will include that -march=core-avx-i would not, in this case, or which flags? Thanks!Nilgai
@Nilgai On this computer (sandybridge), march=sandybridge does not enable AVX (don't know why) while march=native does. Another important difference is that cache sizes are only extracted with march=nativeQuixotism
@BaptisteWicht that's odd seems to work here (I guess): echo | gcc-6 -dM -E - -march=sandybridge | grep AVX #define __AVX__ 1 but cache sizes do seem absent.Nilgai
P
8

I'm going to throw my two cents into this question and suggest a slightly more verbose extension of elias's answer. As of gcc 4.6, running of gcc -march=native -v -E - < /dev/null emits an increasing amount of spam in the form of superfluous -mno-* flags. The following will strip these:

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

However, I have only verified the correctness of this on two different CPUs (an Intel Core2 and AMD Phenom), so I suggest also running the following script to be sure that all of these -mno-* flags can be safely stripped.

2021 EDIT: There are indeed machines where -march=native uses a particular -march value, but must disable some implied ISAs (Instruction Set Architecture) with -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}.$$

I haven't found a difference between gcc -march=native -v -E - < /dev/null and gcc -march=native -### -E - < /dev/null other than some parameters being quoted -- and parameters that contain no special characters, so I'm not sure under what circumstances this makes any real difference.

Finally, note that --march=native was introduced in gcc 4.2, prior to which it is just an unrecognized argument.

Prankster answered 29/1, 2015 at 1:6 Comment(3)
Nice, this gleans has the cache sizes as wellNilgai
gcc version 5.4.0 (Buildroot 2017.05-rc2-00016-gc7eaf50-dirty) returns: Error: unknown architecture `native'Sauterne
Oleg: What arch are you using? It could be that "native" is only supported on some architectures.Prankster
T
1

There is resolve-march-native for exactly this: It parses GCC output and combines the output from multiple calls to GCC into the eventual answer. For example:

# resolve-march-native --vertical
-march=sandybridge
-maes
--param=l1-cache-line-size=64
--param=l1-cache-size=32
--param=l2-cache-size=3072

There is also distccflags but it seems discontinued.

PS: I am the author of resolve-march-native.

Timeconsuming answered 2/12, 2023 at 15:22 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.