# [SOLVED] CFLAGS mistakenly used k8 instead of core2

## jopeto

Hi, I recently installed Gentoo on a Pentium B950 processor and I mistakenly specified -march=k8 instead of core2.

I was wondering - would that cause any problems for the kernel I've compiled as well as all the programs I've installed until now? Should I recompile and reinstall the kernel as well as the programs (if yes, is there an emerge command to recompile and reinstall all packages that have been installed so far?)

Or should I just not worry about it?

PS. On the side is MAKEOPTS="-j3" the right one for this processor? It has 2 CPUs and 1 thread per core.Last edited by jopeto on Wed Aug 01, 2012 7:40 am; edited 1 time in total

----------

## Veldrin

 *Quote:*   

> PS. On the side is MAKEOPTS="-j3" the right one for this processor? It has 2 CPUs and 1 thread per core.

 that is the usual number.

 *Quote:*   

> Or should I just not worry about it? 

 You don't have to worry about the kernel - it dies not use the CFALGS defined in make.conf.

For the other programs, I would worry about 'multimedia' application - or any application that uses ssse3 or 3dnow.

On a sidenote, I was wondering why my core2 built firefox would not run on a phenomII (-march=amdfam10) system. It turned out, that core2 enables ssse3 which is not implemented on a phonomII.

V.

----------

## jopeto

Thanks for your reply. I don't think I've installed any multimedia yet, just Xorg, fvwm, gnumeric, abiword, texlive, gimp and evince I think... So I guess I should be fine. Thanks once again!

----------

## theBlackDragon

 *jopeto wrote:*   

> Should I recompile and reinstall the kernel as well as the programs (if yes, is there an emerge command to recompile and reinstall all packages that have been installed so far?)
> 
> Or should I just not worry about it?

 

```
emerge -e world
```

will get you most of the way there. Don't forget to recompile glibc though.

Also you can use -march=native and it will use the correct flag for your system.

----------

## jopeto

Thank you, this command took a long time, so I guess it must have worked to rebuilt most things. Thanks!

----------

## DaggyStyle

 *jopeto wrote:*   

> Thank you, this command took a long time, so I guess it must have worked to rebuilt most things. Thanks!

 

usually when dealing with CFLAGS change which impacts the system as wide the right course of action is to do the following:

update CFLAGS

reemerge gcc

emerge -e system

emerge -e world

the reason is that if you update the flags and run emerge -e world, all the packages up prior to gcc will be built with gcc based on the old CFLAGS and post gcc packages will be build with the new CFLAGS based gcc. this can create inconsistency within the bins in the code.

----------

## jopeto

OK, thanks a lot. I just completed these commands, so hopefully now everything is taken care of!

----------

## rhill

 *DaggyStyle wrote:*   

> usually when dealing with CFLAGS change which impacts the system as wide the right course of action is to do the following:
> 
> update CFLAGS
> 
> reemerge gcc
> ...

 

Sorry, none of this is true.  The CFLAGS gcc is built with have no effect on the code it outputs.  emerge -e @world was more than enough.

----------

## DaggyStyle

 *dirtyepic wrote:*   

>  *DaggyStyle wrote:*   usually when dealing with CFLAGS change which impacts the system as wide the right course of action is to do the following:
> 
> update CFLAGS
> 
> reemerge gcc
> ...

 

so why do we have march to begin with?

----------

## rhill

 *DaggyStyle wrote:*   

> so why do we have march to begin with?

 

To control the architecture GCC builds code for.  Building GCC with -march=k8 and then compiling with -march=core2 will not make it generate different code than building GCC with -march=core2 and compiling with -march=core2.  That would make it pretty useless as it would be impossible to change.

----------

## DaggyStyle

 *dirtyepic wrote:*   

>  *DaggyStyle wrote:*   so why do we have march to begin with? 
> 
> To control the architecture GCC builds code for.  Building GCC with -march=k8 and then compiling with -march=core2 will not make it generate different code than building GCC with -march=core2 and compiling with -march=core2.  That would make it pretty useless as it would be impossible to change.

 

can you elaborate abit more on this? the march must affect something, question is what?

----------

## DirtyHairy

Differen compiler flags (optimization, march, etc.) will affect the machine code emmitted by the compiler, causing it to perform dfferently on different systems. However, the functionality of the compiled program stays the same (not counting bugs in either the compiler or in the program). The same holds true if you build gcc itself: different flags will affect the machine code of the emmitted gcc binary, but the program logic will not change -> the code emmitted by the newly compiled gcc does not depend on the compiler flags set during its compilation.

----------

## rhill

-march controls what instruction sets are used (on top of the common set for the architecture the compiler was built for, in this case i686), such as MMX, SSE, AVX, etc.  If -mtune isn't specified it also controls what CPU family the code is "tuned" for (things such as scheduling order, instruction grouping, etc - for example if you use -mtune=core2, the compiler prefers using aligned vector loads and stores as they are much more efficient on that CPU, while -mtune=corei7 prefers unaligned, but the generated code would work on either system).  

My point was that the compiler can generate code for any -march option, regardless of the flags used to build the compiler itself.  Building the compiler itself with a different -march setting doesn't change the code the compiler outputs.  That would be fragile and error-prone.  Like Mr. Hairy says, the function of the program does not change, even if the code is optimized in different ways.

The instructions you gave in your original reply are those for upgrading GCC itself, not for changing the CFLAGS of a system.  The original poster probably would have run into issues later on if he had not changed his CFLAGS, but there is no binary compatibility problem.  Bins built with 3DNow instructions would simply not work on his system, regardless of whether they were "mixed" with other libraries or not.  `emerge -e world` was the correct answer.

----------

## DaggyStyle

 *dirtyepic wrote:*   

> -march controls what instruction sets are used (on top of the common set for the architecture the compiler was built for, in this case i686), such as MMX, SSE, AVX, etc.  If -mtune isn't specified it also controls what CPU family the code is "tuned" for (things such as scheduling order, instruction grouping, etc - for example if you use -mtune=core2, the compiler prefers using aligned vector loads and stores as they are much more efficient on that CPU, while -mtune=corei7 prefers unaligned, but the generated code would work on either system).  
> 
> My point was that the compiler can generate code for any -march option, regardless of the flags used to build the compiler itself.  Building the compiler itself with a different -march setting doesn't change the code the compiler outputs.  That would be fragile and error-prone.  Like Mr. Hairy says, the function of the program does not change, even if the code is optimized in different ways.
> 
> The instructions you gave in your original reply are those for upgrading GCC itself, not for changing the CFLAGS of a system.  The original poster probably would have run into issues later on if he had not changed his CFLAGS, but there is no binary compatibility problem.  Bins built with 3DNow instructions would simply not work on his system, regardless of whether they were "mixed" with other libraries or not.  `emerge -e world` was the correct answer.

 

so bins created with -march=core2 and -march=btver2 are identical?

----------

## DirtyHairy

No, binaries generated with different -march options will differ in which set of machine instructions they use, but the program implemented by those instructions will not change. The gcc binaries generated with different -march differ, but there will be no difference in what they do: for a given piece of code, two versions of the same compiler built with different -march settings will emit the same code.

The worst thing that can happen if you run code compiled with an inappropiate march setting is that the program dies when an invalid instruction is encountered. Other than that, nothing will change, just the execution speed might differ.

----------

## DaggyStyle

 *DirtyHairy wrote:*   

> No, binaries generated with different -march options will differ in which set of machine instructions they use, but the program implemented by those instructions will not change. The gcc binaries generated with different -march differ, but there will be no difference in what they do: for a given piece of code, two versions of the same compiler built with different -march settings will emit the same code.
> 
> The worst thing that can happen if you run code compiled with an inappropiate march setting is that the program dies when an invalid instruction is encountered. Other than that, nothing will change, just the execution speed might differ.

 

so if I take a bin from my i7 and run it on first gen AMD phenom it will work?

----------

## DirtyHairy

It may run until the phenom encounters an instruction from the i7 instruction exctensions which it does not implement. At this point, you'll get an invalid instruction exception. However, _if_ it runs, it will behave exactly the same as the same program compiled for the phenom. So, if the program is gcc itself, it might not work, but if it works, it will generate exactly the same code.

What the other dirty and me are saying is _not_ that -march has no influence on the code generated by the compiler, it does change the emmited machine code. However, if you change -march in your CFLAGS, there is no need for compiling things in a specific order, as long as the "old" compiler works, it will behave exactly the same as the "new" compiler. If the old -march was compatible with your system, then there isn't any pressing need to recompile anything at all, you can just let the change trickle through as you (re)emerge packes over time, no inconsistencies will be introduced this way. Only if the old -march was potentially incompatible with your system or if you _want_ to immediately apply the changed -march to your system for another reason you have to reemerge the system, but order does not matter.

----------

## DaggyStyle

 *DirtyHairy wrote:*   

> It may run until the phenom encounters an instruction from the i7 instruction exctensions which it does not implement. At this point, you'll get an invalid instruction exception. However, _if_ it runs, it will behave exactly the same as the same program compiled for the phenom. So, if the program is gcc itself, it might not work, but if it works, it will generate exactly the same code.
> 
> What the other dirty and me are saying is _not_ that -march has no influence on the code generated by the compiler, it does change the emmited machine code. However, if you change -march in your CFLAGS, there is no need for compiling things in a specific order, as long as the "old" compiler works, it will behave exactly the same as the "new" compiler. If the old -march was compatible with your system, then there isn't any pressing need to recompile anything at all, you can just let the change trickle through as you (re)emerge packes over time, no inconsistencies will be introduced this way. Only if the old -march was potentially incompatible with your system or if you _want_ to immediately apply the changed -march to your system for another reason you have to reemerge the system, but order does not matter.

 

ok, so to sum it up:

-march does generate different bins.

error will occur only when the cpu encounters a unknown instruction.

recompiling gcc followed but world is a good idea to benefit the new -march but not a must if no issue is encountered.

----------

## DirtyHairy

There is no need to recompile gcc before compiling world.

----------

## mv

If you need to make sure that everything uses the new CFLAGS (e.g. because you have a production system, and the old CFLAGS would produce illegal code for your architecture), then you have to run emerge -e @world twice:

The reason is that there are some programs which take their CFLAGS from some stored position (e.g. some perl modules "inherit" the cflags perl was compiled with; IIRC there was something similar happening with some "bad" usage of pkgconf - problem is that it is almost impossible to predict which programs require this unless you inspect every single program which probably nobody does.)

----------

## rhill

If you're doing `emerge -e world` then you should be rebuilding everything in dependency order, ie. you'll be rebuilding perl before any perl modules.  That's a big should though, as it assumes every package's dependencies are correct and complete.  So yeah, wouldn't hurt.

----------

## mv

 *dirtyepic wrote:*   

> If you're doing `emerge -e world` then you should be rebuilding everything in dependency order, ie. you'll be rebuilding perl before any perl modules.

 

There are enough "dependency loops" in the tree such that any dependency order may be wrong. Then there is the issue with .la files (some are really needed if there is no pkgconf substitute) which can also feed CFLAGS and thus theoretically break even more things (such that actually even emerge -e @world twice might be non-sufficient). However, I guess these cases are meanwhile so rare that they can be neglected.

----------

