Project:Quality Assurance/User vs upstream FLAGS

From Gentoo Wiki
Jump to: navigation, search
This page is a work in progress by MGorny (talk | contribs). Treat its contents with caution.

This guide aims to provide a quick reference of which *FLAGS can be forced by upstream, which can be forced by the ebuild, and which should be removed and left for user control.

Generic policy

The generic policy is that user-provided *FLAGS should be respected, unless there is a very good reason not to use them. If some combinations of flags are known to cause breakages on the package, ebuilds can strip them as necessary.

User-provided *FLAGS can be only ignored if there is a very good reason to do so. Those include special targets (e.g. building bootloader code). Usually, USE=custom-cflags should be provided to allow user to force his flags anyway.

Upstream packages should not force any optimization or debugging flags, and respect all optimization and debugging flags passed by the user. However, they can append additional quasi-optimization flags if they can not be used safely as a global flags (i.e. rely on specific deviations from the standards) and only indicate that the code is safe for those optimizations. See the tables below for specific flags.

If upstream forces a disallowed flag, the ebuild should prevent that from happening (e.g. for autotools, you can commonly override the cache variable detecting whether it is supported).

The ebuild can also provide additional allowed flags on the ebuild author leisure. However, it is recommended to pass the flags on to upstream instead.

USE flags should not be used to control *FLAGS (except for USE=custom-cflags). Especially, USE=debug should be only used to control debug behavior other than -g flags (and it should not force them anyway), e.g. -DNDEBUG. CPU_FLAGS_* should be used to control assembly and not passing -m flags -- and the latter should be passed by user (mostly implicitly via -march).


Rule of thumb: look at gcc(1) manpage. Flags from C Language Options, C++ Language Options... and Code Generation Options are safe to use upstream. The flags from Debugging Options, Optimization Options and Machine Dependent Options usually should be only set by user, except for those allowed in the table following.

Flag Allowed upstream? Description
-O* No (with exceptions) Controls optimization profile used by the compiler. Generally should not be overriden upstream to let user control it with specific level of optimization, reliability and debugging-friendliness as necessary. However, it is generally acceptable to reduce optimization level as a temporary work-around if a higher level is known to break the package, with note that disabling specific optimizations or fixing the package code are the preferred solutions.

Note: generally it is not necessary to strip upstream -O flags if user C*FLAGS are appended to them, as user's -O* will override the upstream default.

-Werror No Turns all compiler warnings into errors. This is not acceptable as different compilers and compiler versions can introduce additional warnings that are unforeseen upstream, and that will cause the packages to fail to build for end users, often for minor reasons.
-Werror=* Discouraged Turns specific compiler warnings into errors. It is acceptable to leave it since usually the scope is narrow enough not to cause additional errors beyond what upstream has already seen. However, there is still some risk that new compiler versions will catch additional issues under the same warning flag, and therefore cause the packages to fail to build for end users.
-ffast-math (and like) Yes Enables multiple flags that allow non-standard math behavior (see gcc(1) for complete list and descriptions). This can't be enabled globally since it breaks standard-compliant programs. At the same time, it should be perfectly safe to use it on programs written in that limitation in mind.
-fmerge-all-constants Yes Enables merging of identical constants and variables. This can't be enabled globally since it can result in multiple distinct constant variables using the same address, and therefore breaking the programs relying on their distinct addresses. It should be safe for programs written with that limitation in mind.
-funsafe-loop-optimizations Yes Enables optimizations relying on the assumption that loop indices do not overflow, and that loops with nontrivial exit conditions are not infinite. This can't be enabled globally as it could break programs not meeting the forementioned conditions. It should be safe for programs written with those limitations in mind.
-flto No Enables link-time optimization, i.e. delaying all code optimizations until link time. This should not be enabled out of the box as it increases build time and memory use significantly, and reduces parallel make, ccache and distcc efficiency. At the same time, user can mostly-safely enable it globally or per-package.

Note: introducing a 'lto' USE flag for this purpose is a bad idea as we do not introduce USE flags to append CFLAGS but let user control CFLAGS directly.

-m* Under specific conditions Flags like -mmmx can be used to enable code relying on specific processor characteristics. Using those flags is discouraged; however, they are acceptable if they are necessary to build assembly code and the scenario guarantees that it will not regress on CPUs missing the specific instruction sets or not matching the specific characteristics.

Acceptable examples are packages using CPU_FLAGS* flags to control optional assembly (however, using C*FLAGS to determine available instructions is preferable), compiling optional code whose use is determined at runtime or code that unconditionally relies on specific assembly.