mirror of
https://github.com/flatcar/scripts.git
synced 2025-08-31 19:31:07 +02:00
eclass/flag-o-matic: Sync with Gentoo
It's from Gentoo commit 1c907885fa271f0077f7c4ed03f44619b2350e5c.
This commit is contained in:
parent
18aa6014c2
commit
99e1ad5b6f
@ -1,21 +1,18 @@
|
||||
# Copyright 1999-2021 Gentoo Authors
|
||||
# Copyright 1999-2022 Gentoo Authors
|
||||
# Distributed under the terms of the GNU General Public License v2
|
||||
|
||||
# Flatcar: Support EAPI 0 and 4.
|
||||
|
||||
# @ECLASS: flag-o-matic.eclass
|
||||
# @MAINTAINER:
|
||||
# toolchain@gentoo.org
|
||||
# @SUPPORTED_EAPIS: 0 4 5 6 7 8
|
||||
# @SUPPORTED_EAPIS: 6 7 8
|
||||
# @BLURB: common functions to manipulate and query toolchain flags
|
||||
# @DESCRIPTION:
|
||||
# This eclass contains a suite of functions to help developers sanely
|
||||
# and safely manage toolchain flags in their builds.
|
||||
|
||||
case ${EAPI:-0} in
|
||||
1|2|3) die "flag-o-matic.eclass: EAPI ${EAPI} is too old." ;;
|
||||
0|4|5|6|7|8) ;;
|
||||
*) die "EAPI ${EAPI} is not supported by flag-o-matic.eclass." ;;
|
||||
case ${EAPI} in
|
||||
6|7|8) ;;
|
||||
*) die "${ECLASS}: EAPI ${EAPI:-0} not supported" ;;
|
||||
esac
|
||||
|
||||
if [[ -z ${_FLAG_O_MATIC_ECLASS} ]]; then
|
||||
@ -23,11 +20,11 @@ _FLAG_O_MATIC_ECLASS=1
|
||||
|
||||
inherit toolchain-funcs
|
||||
|
||||
[[ ${EAPI:-0} == [04567] ]] && inherit eutils
|
||||
[[ ${EAPI} == [67] ]] && inherit eutils
|
||||
|
||||
# @FUNCTION: all-flag-vars
|
||||
# @DESCRIPTION:
|
||||
# Return all the flag variables that our high level funcs operate on.
|
||||
# Return all the flag variables that our high level functions operate on.
|
||||
all-flag-vars() {
|
||||
echo {ADA,C,CPP,CXX,CCAS,F,FC,LD}FLAGS
|
||||
}
|
||||
@ -38,8 +35,8 @@ all-flag-vars() {
|
||||
# {C,CPP,CXX,CCAS,F,FC,LD}FLAGS that we allow in strip-flags
|
||||
# Note: shell globs and character lists are allowed
|
||||
setup-allowed-flags() {
|
||||
[[ ${EAPI:-0} == [04567] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI:-0}."
|
||||
[[ ${EAPI} == [67] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI}."
|
||||
_setup-allowed-flags "$@"
|
||||
}
|
||||
|
||||
@ -50,21 +47,39 @@ setup-allowed-flags() {
|
||||
# Note: shell globs and character lists are allowed
|
||||
_setup-allowed-flags() {
|
||||
ALLOWED_FLAGS=(
|
||||
-pipe -O '-O[12sg]' -mcpu -march -mtune
|
||||
'-fstack-protector*'
|
||||
'-fsanitize*' '-fno-sanitize*'
|
||||
'-fstack-check*' -fno-stack-check
|
||||
-fbounds-check -fbounds-checking -fno-strict-overflow
|
||||
-fno-PIE -fno-pie -nopie -no-pie -fno-unit-at-a-time
|
||||
-pipe -O '-O[12sg]' '-mcpu=*' '-march=*' '-mtune=*'
|
||||
|
||||
# debugging symbols should generally be very safe to add
|
||||
# Hardening flags
|
||||
'-fstack-protector*'
|
||||
'-fstack-check*' -fno-stack-check
|
||||
-fstack-clash-protection
|
||||
'-fcf-protection=*'
|
||||
-fbounds-check -fbounds-checking
|
||||
-fno-PIE -fno-pie -nopie -no-pie
|
||||
# Spectre mitigations, bug #646076
|
||||
'-mindirect-branch=*'
|
||||
-mindirect-branch-register
|
||||
'-mfunction-return=*'
|
||||
-mretpoline
|
||||
|
||||
# Misc
|
||||
-fno-unit-at-a-time -fno-strict-overflow
|
||||
|
||||
# Sanitizers
|
||||
'-fsanitize*' '-fno-sanitize*'
|
||||
|
||||
# Debugging symbols should generally be very safe to add
|
||||
-g '-g[0-9]'
|
||||
-ggdb '-ggdb[0-9]'
|
||||
-gdwarf '-gdwarf-*'
|
||||
-gstabs -gstabs+
|
||||
-gz
|
||||
-glldb
|
||||
|
||||
# Cosmetic/output related, see e.g. bug #830534
|
||||
-fno-diagnostics-color '-fmessage-length=*'
|
||||
-fno-ident -fpermissive -frecord-gcc-switches
|
||||
-frecord-command-line
|
||||
'-fdiagnostics*' '-fplugin*'
|
||||
'-W*' -w
|
||||
|
||||
@ -72,7 +87,7 @@ _setup-allowed-flags() {
|
||||
'-[DUILR]*' '-Wl,*'
|
||||
|
||||
# Linker choice flag
|
||||
'-fuse-ld'
|
||||
'-fuse-ld=*'
|
||||
)
|
||||
|
||||
# allow a bunch of flags that negate features / control ABI
|
||||
@ -82,19 +97,22 @@ _setup-allowed-flags() {
|
||||
-fno-omit-frame-pointer '-fno-builtin*'
|
||||
)
|
||||
ALLOWED_FLAGS+=(
|
||||
-mregparm -mno-app-regs -mapp-regs -mno-mmx -mno-sse
|
||||
'-mregparm=*' -mno-app-regs -mapp-regs -mno-mmx -mno-sse
|
||||
-mno-sse2 -mno-sse3 -mno-ssse3 -mno-sse4 -mno-sse4.1 -mno-sse4.2
|
||||
-mno-avx -mno-aes -mno-pclmul -mno-sse4a -mno-3dnow -mno-popcnt
|
||||
-mno-abm -mips1 -mips2 -mips3 -mips4 -mips32 -mips64 -mips16 -mplt
|
||||
-msoft-float -mno-soft-float -mhard-float -mno-hard-float -mfpu
|
||||
-mieee -mieee-with-inexact -mschedule -mfloat-gprs -mspe -mno-spe
|
||||
-msoft-float -mno-soft-float -mhard-float -mno-hard-float '-mfpu=*'
|
||||
-mieee -mieee-with-inexact '-mschedule=*' -mfloat-gprs -mspe -mno-spe
|
||||
-mtls-direct-seg-refs -mno-tls-direct-seg-refs -mflat -mno-flat
|
||||
-mno-faster-structs -mfaster-structs -m32 -m64 -mx32 -mabi
|
||||
-mlittle-endian -mbig-endian -EL -EB -fPIC -mlive-g0 -mcmodel
|
||||
-mstack-bias -mno-stack-bias -msecure-plt '-m*-toc' -mfloat-abi
|
||||
-mno-faster-structs -mfaster-structs -m32 -m64 -mx32 '-mabi=*'
|
||||
-mlittle-endian -mbig-endian -EL -EB -fPIC -mlive-g0 '-mcmodel=*'
|
||||
-mstack-bias -mno-stack-bias -msecure-plt '-m*-toc' '-mfloat-abi=*'
|
||||
-mfix-r4000 -mno-fix-r4000 -mfix-r4400 -mno-fix-r4400
|
||||
-mfix-rm7000 -mno-fix-rm7000 -mfix-r10000 -mno-fix-r10000
|
||||
-mr10k-cache-barrier -mthumb -marm
|
||||
'-mr10k-cache-barrier=*' -mthumb -marm
|
||||
|
||||
# needed for arm64 (and in particular SCS)
|
||||
-ffixed-x18
|
||||
|
||||
# gcc 4.5
|
||||
-mno-fma4 -mno-movbe -mno-xop -mno-lwp
|
||||
@ -191,6 +209,7 @@ filter-flags() {
|
||||
# Remove flags that enable Large File Support.
|
||||
filter-lfs-flags() {
|
||||
[[ $# -ne 0 ]] && die "filter-lfs-flags takes no arguments"
|
||||
|
||||
# http://www.gnu.org/s/libc/manual/html_node/Feature-Test-Macros.html
|
||||
# _LARGEFILE_SOURCE: enable support for new LFS funcs (ftello/etc...)
|
||||
# _LARGEFILE64_SOURCE: enable support for 64bit variants (off64_t/fseeko64/etc...)
|
||||
@ -199,6 +218,14 @@ filter-lfs-flags() {
|
||||
filter-flags -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE -D_TIME_BITS=64
|
||||
}
|
||||
|
||||
# @FUNCTION: filter-lto
|
||||
# @DESCRIPTION:
|
||||
# Remove flags that enable LTO and those that depend on it
|
||||
filter-lto() {
|
||||
[[ $# -ne 0 ]] && die "filter-lto takes no arguments"
|
||||
filter-flags '-flto*' -fwhole-program-vtables '-fsanitize=cfi*'
|
||||
}
|
||||
|
||||
# @FUNCTION: filter-ldflags
|
||||
# @USAGE: <flags>
|
||||
# @DESCRIPTION:
|
||||
@ -228,7 +255,7 @@ append-cppflags() {
|
||||
# @CODE
|
||||
append-cflags() {
|
||||
[[ $# -eq 0 ]] && return 0
|
||||
# Do not do automatic flag testing ourselves. #417047
|
||||
# Do not do automatic flag testing ourselves, bug #417047
|
||||
export CFLAGS+=" $*"
|
||||
return 0
|
||||
}
|
||||
@ -243,7 +270,7 @@ append-cflags() {
|
||||
# @CODE
|
||||
append-cxxflags() {
|
||||
[[ $# -eq 0 ]] && return 0
|
||||
# Do not do automatic flag testing ourselves. #417047
|
||||
# Do not do automatic flag testing ourselves, bug #417047
|
||||
export CXXFLAGS+=" $*"
|
||||
return 0
|
||||
}
|
||||
@ -258,7 +285,7 @@ append-cxxflags() {
|
||||
# @CODE
|
||||
append-fflags() {
|
||||
[[ $# -eq 0 ]] && return 0
|
||||
# Do not do automatic flag testing ourselves. #417047
|
||||
# Do not do automatic flag testing ourselves, bug #417047
|
||||
export FFLAGS+=" $*"
|
||||
export FCFLAGS+=" $*"
|
||||
return 0
|
||||
@ -269,7 +296,8 @@ append-fflags() {
|
||||
# Add flags that enable Large File Support.
|
||||
append-lfs-flags() {
|
||||
[[ $# -ne 0 ]] && die "append-lfs-flags takes no arguments"
|
||||
# see comments in filter-lfs-flags func for meaning of these
|
||||
|
||||
# See comments in filter-lfs-flags func for meaning of these
|
||||
append-cppflags -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE
|
||||
}
|
||||
|
||||
@ -296,9 +324,9 @@ append-ldflags() {
|
||||
append-flags() {
|
||||
[[ $# -eq 0 ]] && return 0
|
||||
case " $* " in
|
||||
*' '-[DIU]*) eqawarn 'please use append-cppflags for preprocessor flags' ;;
|
||||
*' '-[DIU]*) eqawarn 'Please use append-cppflags for preprocessor flags' ;;
|
||||
*' '-L*|\
|
||||
*' '-Wl,*) eqawarn 'please use append-ldflags for linker flags' ;;
|
||||
*' '-Wl,*) eqawarn 'Please use append-ldflags for linker flags' ;;
|
||||
esac
|
||||
append-cflags "$@"
|
||||
append-cxxflags "$@"
|
||||
@ -454,9 +482,8 @@ strip-flags() {
|
||||
local new=()
|
||||
|
||||
for x in ${!var} ; do
|
||||
local flag=${x%%=*}
|
||||
for y in "${ALLOWED_FLAGS[@]}" ; do
|
||||
if [[ -z ${flag%%${y}} ]] ; then
|
||||
if [[ ${x} == ${y} ]] ; then
|
||||
new+=( "${x}" )
|
||||
break
|
||||
fi
|
||||
@ -486,8 +513,8 @@ strip-flags() {
|
||||
# Returns shell true if <flag> is supported by given <compiler>,
|
||||
# else returns shell false.
|
||||
test-flag-PROG() {
|
||||
[[ ${EAPI:-0} == [04567] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI:-0}."
|
||||
[[ ${EAPI} == [67] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI}."
|
||||
_test-flag-PROG "$@"
|
||||
}
|
||||
|
||||
@ -547,6 +574,15 @@ _test-flag-PROG() {
|
||||
c+ld)
|
||||
in_ext='c'
|
||||
in_src='int main(void) { return 0; }'
|
||||
|
||||
if is-ldflagq -fuse-ld=* ; then
|
||||
# Respect linker chosen by user so we don't
|
||||
# end up giving false results by checking
|
||||
# with default linker. bug #832377
|
||||
fuse_ld_value=$(get-flag -fuse-ld=*)
|
||||
cmdline_extra+=(${fuse_ld_value})
|
||||
fi
|
||||
|
||||
cmdline_extra+=(-xc)
|
||||
;;
|
||||
esac
|
||||
@ -556,7 +592,7 @@ _test-flag-PROG() {
|
||||
printf "%s\n" "${in_src}" > "${test_in}" || die "Failed to create '${test_in}'"
|
||||
|
||||
# Currently we rely on warning-free output of a compiler
|
||||
# before the flag to see if a flag prduces any warnings.
|
||||
# before the flag to see if a flag produces any warnings.
|
||||
# This has a few drawbacks:
|
||||
# - if compiler already generates warnings we filter out
|
||||
# every single flag: bug #712488
|
||||
@ -582,7 +618,9 @@ _test-flag-PROG() {
|
||||
# -Werror makes clang bail out on unused arguments as well;
|
||||
# try to add -Qunused-arguments to work-around that
|
||||
# other compilers don't support it but then, it's failure like
|
||||
# any other
|
||||
# any other.
|
||||
#
|
||||
# See also bug #712488 and bug #714742.
|
||||
cmdline+=( -Qunused-arguments )
|
||||
"${cmdline[@]}" &>/dev/null
|
||||
fi
|
||||
@ -625,8 +663,8 @@ test-flag-CCLD() { _test-flag-PROG CC c+ld "$@"; }
|
||||
# Returns shell true if <flags> are supported by given <compiler>,
|
||||
# else returns shell false.
|
||||
test-flags-PROG() {
|
||||
[[ ${EAPI:-0} == [04567] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI:-0}."
|
||||
[[ ${EAPI} == [67] ]] ||
|
||||
die "Internal function ${FUNCNAME} is not available in EAPI ${EAPI}."
|
||||
_test-flags-PROG "$@"
|
||||
}
|
||||
|
||||
@ -647,7 +685,7 @@ _test-flags-PROG() {
|
||||
|
||||
while (( $# )); do
|
||||
case "$1" in
|
||||
# '-B /foo': bug # 687198
|
||||
# '-B /foo': bug #687198
|
||||
--param|-B)
|
||||
if test-flag-${comp} "$1" "$2"; then
|
||||
flags+=( "$1" "$2" )
|
||||
@ -833,7 +871,7 @@ raw-ldflags() {
|
||||
x=${x#-Wl,}
|
||||
set -- "$@" ${x//,/ }
|
||||
;;
|
||||
*) # Assume it's a compiler driver flag, so throw it away #441808
|
||||
*) # Assume it's a compiler driver flag, so throw it away, bug #441808
|
||||
;;
|
||||
esac
|
||||
done
|
||||
@ -850,4 +888,150 @@ no-as-needed() {
|
||||
esac
|
||||
}
|
||||
|
||||
# @FUNCTION: _test-compile-PROG
|
||||
# @USAGE: <language> <code>
|
||||
# @INTERNAL
|
||||
# @DESCRIPTION:
|
||||
# Attempts to compile (and possibly link) the given program. The first
|
||||
# <language> parameter corresponds to the standard -x compiler argument.
|
||||
# If the program should additionally be attempted to be linked, the string
|
||||
# "+ld" should be added to the <language> parameter.
|
||||
_test-compile-PROG() {
|
||||
local lang=$1
|
||||
local code=$2
|
||||
shift 2
|
||||
|
||||
[[ -z "${lang}" ]] && return 1
|
||||
[[ -z "${code}" ]] && return 1
|
||||
|
||||
local compiler filename_in filename_out args=() libs=()
|
||||
case "${lang}" in
|
||||
c)
|
||||
compiler="$(tc-getCC)"
|
||||
filename_in="${T}/test.c"
|
||||
filename_out="${T}/test.o"
|
||||
args+=(${CFLAGS[@]} -xc -c)
|
||||
;;
|
||||
c++)
|
||||
compiler="$(tc-getCXX)"
|
||||
filename_in="${T}/test.cc"
|
||||
filename_out="${T}/test.o"
|
||||
args+=(${CXXFLAGS[@]} -xc++ -c)
|
||||
;;
|
||||
f77)
|
||||
compiler="$(tc-getF77)"
|
||||
filename_in="${T}/test.f"
|
||||
filename_out="${T}/test.o"
|
||||
args+=(${FFFLAGS[@]} -xf77 -c)
|
||||
;;
|
||||
f95)
|
||||
compiler="$(tc-getFC)"
|
||||
filename_in="${T}/test.f90"
|
||||
filename_out="${T}/test.o"
|
||||
args+=(${FCFLAGS[@]} -xf95 -c)
|
||||
;;
|
||||
c+ld)
|
||||
compiler="$(tc-getCC)"
|
||||
filename_in="${T}/test.c"
|
||||
filename_out="${T}/test.exe"
|
||||
args+=(${CFLAGS[@]} ${LDFLAGS[@]} -xc)
|
||||
libs+=(${LIBS[@]})
|
||||
;;
|
||||
c+++ld)
|
||||
compiler="$(tc-getCXX)"
|
||||
filename_in="${T}/test.cc"
|
||||
filename_out="${T}/test.exe"
|
||||
args+=(${CXXFLAGS[@]} ${LDFLAGS[@]} -xc++)
|
||||
libs+=(${LIBS[@]})
|
||||
;;
|
||||
f77+ld)
|
||||
compiler="$(tc-getF77)"
|
||||
filename_in="${T}/test.f"
|
||||
filename_out="${T}/test.exe"
|
||||
args+=(${FFLAGS[@]} ${LDFLAGS[@]} -xf77)
|
||||
libs+=(${LIBS[@]})
|
||||
;;
|
||||
f95+ld)
|
||||
compiler="$(tc-getFC)"
|
||||
filename_in="${T}/test.f90"
|
||||
filename_out="${T}/test.exe"
|
||||
args+=(${FCFLAGS[@]} ${LDFLAGS[@]} -xf95)
|
||||
libs+=(${LIBS[@]})
|
||||
;;
|
||||
*)
|
||||
die "Unknown compiled language ${lang}"
|
||||
;;
|
||||
esac
|
||||
|
||||
printf "%s\n" "${code}" > "${filename_in}" || die "Failed to create '${test_in}'"
|
||||
|
||||
"${compiler}" ${args[@]} "${filename_in}" -o "${filename_out}" ${libs[@]} &>/dev/null
|
||||
}
|
||||
|
||||
# @FUNCTION: append-atomic-flags
|
||||
# @USAGE: [bytes]
|
||||
# @DESCRIPTION:
|
||||
# Attempts to detect if appending -latomic is required to use
|
||||
# a specific-sized atomic intrinsic, and if so, appends it. If the bytesize
|
||||
# is not specified, then check the four most common byte sizes (1, 2, 4, 8).
|
||||
# >=16-byte atomics are not included in this default set and must be explicitly
|
||||
# passed if required. This may require you to add a macro definition like
|
||||
# -Duint128_t=__uint128_t to your CFLAGS.
|
||||
append-atomic-flags() {
|
||||
# this implementation is as described in bug #820101
|
||||
local code
|
||||
|
||||
# first, ensure we can compile a trivial program
|
||||
# this is because we can't distinguish if _test-compile-PROG
|
||||
# fails because -latomic is actually needed or if we have a
|
||||
# broken toolchain (like due to bad FLAGS)
|
||||
read -r -d '' code <<- EOF
|
||||
int main()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
EOF
|
||||
|
||||
# if toolchain is broken, just return silently. it's better to
|
||||
# let other pieces of the build fail later down the line than to
|
||||
# make people think that something to do with atomic support is the
|
||||
# cause of their problems.
|
||||
_test-compile-PROG "c+ld" "${code}" || return
|
||||
|
||||
local bytesizes
|
||||
[[ "${#}" == "0" ]] && bytesizes=( "1" "2" "4" "8" ) || bytesizes="${@}"
|
||||
|
||||
for bytesize in ${bytesizes[@]}
|
||||
do
|
||||
# this sample program is informed by the great testing from the buildroot project:
|
||||
# https://github.com/buildroot/buildroot/commit/6856e417da4f3aa77e2a814db2a89429af072f7d
|
||||
read -r -d '' code <<- EOF
|
||||
#include <stdint.h>
|
||||
int main()
|
||||
{
|
||||
uint$((${bytesize} * 8))_t a = 0;
|
||||
__atomic_add_fetch(&a, 3, __ATOMIC_RELAXED);
|
||||
__atomic_compare_exchange_n(&a, &a, 2, 1, __ATOMIC_RELAXED, __ATOMIC_RELAXED);
|
||||
return 0;
|
||||
}
|
||||
EOF
|
||||
|
||||
# do nothing if test program links fine
|
||||
_test-compile-PROG "c+ld" "${code}" && continue
|
||||
|
||||
# ensure that the toolchain supports -latomic
|
||||
test-flags-CCLD "-latomic" &>/dev/null || die "-latomic is required but not supported by $(tc-getCC)"
|
||||
|
||||
append-libs "-latomic"
|
||||
|
||||
# verify that this did indeed fix the problem
|
||||
_test-compile-PROG "c+ld" "${code}" || \
|
||||
die "libatomic does not include an implementation of ${bytesize}-byte atomics for this toolchain"
|
||||
|
||||
# if any of the required bytesizes require -latomic, no need to continue
|
||||
# checking the others
|
||||
return
|
||||
done
|
||||
}
|
||||
|
||||
fi
|
||||
|
Loading…
x
Reference in New Issue
Block a user