Why does `gcc -Q -march = corei7-avx --help = target` lie?

If we request that -march=native expand, the result seems as it should be

 $ 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] 

But if the architecture is specified directly, gcc removes the SSE flags that it allows for native , why?

  $ 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] 

Compiling with -march=corei7-avx , however, indicates that they will be included.

 $ 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 
+6
source share
2 answers

I guess a little, but anyway it is too long for comment ...

Take a look at the output of this command:

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

And this is different:

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

The interesting part is calling the binary cc1 . In the case of -march=native it is replaced with all the target parameters, and not just the equivalent -march . I have sandybridge , so in my car it gives:

 .../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 ... 

While adding -march=corei7-avx or ( -march=sandybridge in my case) there are none of these specific architecture parameters.

Now my conclusion:

The output -Q --help=target indicates whether the specified compiler options are set, and not if the function is enabled or not. As it happens, some of these functions can be turned on or off in different ways.

For example, SSE can be enabled using -msse , as well as using -march=corei7-avx or -march=sandybridge . But although specifying -march=corei7-avx allows SSE, it does not set the -msse options as such.

On the other hand, -march=native sets many options, not just the actual -march , but also any other relevant parameter that can be extracted from the runtime system, such as cache sizes.

The correct way to check the inclusion or deactivation of a certain function is, as you have already noticed, checking the predefined defines .

+3
source

This is a known bug in GCC (39851) ; It was opened after GCC 4.5 in 2009.

+3
source

Source: https://habr.com/ru/post/979429/


All Articles