Merge remote-tracking branch 'github/pr/608'.
[gentoo.git] / eclass / toolchain.eclass
1 # Copyright 1999-2015 Gentoo Foundation
2 # Distributed under the terms of the GNU General Public License v2
3 # $Id$
4
5 # Maintainer: Toolchain Ninjas <toolchain@gentoo.org>
6
7 DESCRIPTION="The GNU Compiler Collection"
8 HOMEPAGE="https://gcc.gnu.org/"
9 RESTRICT="strip" # cross-compilers need controlled stripping
10
11 inherit eutils fixheadtails flag-o-matic gnuconfig libtool multilib pax-utils toolchain-funcs versionator
12
13 if [[ ${PV} == *_pre9999* ]] ; then
14         EGIT_REPO_URI="git://gcc.gnu.org/git/gcc.git"
15         # naming style:
16         # gcc-4.7.1_pre9999 -> gcc-4_7-branch
17         #  Note that the micro version is required or lots of stuff will break.
18         #  To checkout master set gcc_LIVE_BRANCH="master" in the ebuild before
19         #  inheriting this eclass.
20         EGIT_BRANCH="${PN}-${PV%.?_pre9999}-branch"
21         EGIT_BRANCH=${EGIT_BRANCH//./_}
22         inherit git-2
23 fi
24
25 FEATURES=${FEATURES/multilib-strict/}
26
27 EXPORTED_FUNCTIONS="pkg_setup src_unpack src_compile src_test src_install pkg_postinst pkg_postrm"
28 case ${EAPI:-0} in
29         0|1)    die "Need to upgrade to at least EAPI=2";;
30         2|3)    EXPORTED_FUNCTIONS+=" src_prepare src_configure" ;;
31         4*|5*)  EXPORTED_FUNCTIONS+=" pkg_pretend src_prepare src_configure" ;;
32         *)      die "I don't speak EAPI ${EAPI}."
33 esac
34 EXPORT_FUNCTIONS ${EXPORTED_FUNCTIONS}
35
36 #---->> globals <<----
37
38 export CTARGET=${CTARGET:-${CHOST}}
39 if [[ ${CTARGET} = ${CHOST} ]] ; then
40         if [[ ${CATEGORY} == cross-* ]] ; then
41                 export CTARGET=${CATEGORY#cross-}
42         fi
43 fi
44 : ${TARGET_ABI:=${ABI}}
45 : ${TARGET_MULTILIB_ABIS:=${MULTILIB_ABIS}}
46 : ${TARGET_DEFAULT_ABI:=${DEFAULT_ABI}}
47
48 is_crosscompile() {
49         [[ ${CHOST} != ${CTARGET} ]]
50 }
51
52 # General purpose version check.  Without a second arg matches up to minor version (x.x.x)
53 tc_version_is_at_least() {
54         version_is_at_least "$1" "${2:-${GCC_RELEASE_VER}}"
55 }
56
57 # General purpose version range check
58 # Note that it matches up to but NOT including the second version
59 tc_version_is_between() {
60         tc_version_is_at_least "${1}" && ! tc_version_is_at_least "${2}"
61 }
62
63 GCC_PV=${TOOLCHAIN_GCC_PV:-${PV}}
64 GCC_PVR=${GCC_PV}
65 [[ ${PR} != "r0" ]] && GCC_PVR=${GCC_PVR}-${PR}
66 GCC_RELEASE_VER=$(get_version_component_range 1-3 ${GCC_PV})
67 GCC_BRANCH_VER=$(get_version_component_range 1-2 ${GCC_PV})
68 GCCMAJOR=$(get_version_component_range 1 ${GCC_PV})
69 GCCMINOR=$(get_version_component_range 2 ${GCC_PV})
70 GCCMICRO=$(get_version_component_range 3 ${GCC_PV})
71 [[ ${BRANCH_UPDATE-notset} == "notset" ]] && \
72         BRANCH_UPDATE=$(get_version_component_range 4 ${GCC_PV})
73
74 # According to gcc/c-cppbuiltin.c, GCC_CONFIG_VER MUST match this regex.
75 # ([^0-9]*-)?[0-9]+[.][0-9]+([.][0-9]+)?([- ].*)?
76 GCC_CONFIG_VER=${GCC_CONFIG_VER:-$(replace_version_separator 3 '-' ${GCC_PV})}
77
78 # Pre-release support
79 if [[ ${GCC_PV} == *_pre* ]] ; then
80         PRERELEASE=${GCC_PV/_pre/-}
81 elif [[ ${GCC_PV} == *_alpha* ]] ; then
82         SNAPSHOT=${GCC_BRANCH_VER}-${GCC_PV##*_alpha}
83 elif [[ ${GCC_PV} == *_beta* ]] ; then
84         SNAPSHOT=${GCC_BRANCH_VER}-${GCC_PV##*_beta}
85 elif [[ ${GCC_PV} == *_rc* ]] ; then
86         SNAPSHOT=${GCC_PV%_rc*}-RC-${GCC_PV##*_rc}
87 fi
88
89 if [[ ${SNAPSHOT} == [56789].0-* ]] ; then
90         # The gcc-5+ releases have dropped the .0 for some reason.
91         SNAPSHOT=${SNAPSHOT/.0}
92 fi
93
94 export GCC_FILESDIR=${GCC_FILESDIR:-${FILESDIR}}
95
96 PREFIX=${TOOLCHAIN_PREFIX:-/usr}
97
98 if tc_version_is_at_least 3.4.0 ; then
99         LIBPATH=${TOOLCHAIN_LIBPATH:-${PREFIX}/lib/gcc/${CTARGET}/${GCC_CONFIG_VER}}
100 else
101         LIBPATH=${TOOLCHAIN_LIBPATH:-${PREFIX}/lib/gcc-lib/${CTARGET}/${GCC_CONFIG_VER}}
102 fi
103 INCLUDEPATH=${TOOLCHAIN_INCLUDEPATH:-${LIBPATH}/include}
104
105 if is_crosscompile ; then
106         BINPATH=${TOOLCHAIN_BINPATH:-${PREFIX}/${CHOST}/${CTARGET}/gcc-bin/${GCC_CONFIG_VER}}
107         HOSTLIBPATH=${PREFIX}/${CHOST}/${CTARGET}/lib/${GCC_CONFIG_VER}
108 else
109         BINPATH=${TOOLCHAIN_BINPATH:-${PREFIX}/${CTARGET}/gcc-bin/${GCC_CONFIG_VER}}
110 fi
111
112 DATAPATH=${TOOLCHAIN_DATAPATH:-${PREFIX}/share/gcc-data/${CTARGET}/${GCC_CONFIG_VER}}
113
114 # Dont install in /usr/include/g++-v3/, but in gcc internal directory.
115 # We will handle /usr/include/g++-v3/ with gcc-config ...
116 STDCXX_INCDIR=${TOOLCHAIN_STDCXX_INCDIR:-${LIBPATH}/include/g++-v${GCC_BRANCH_VER/\.*/}}
117
118 #---->> LICENSE+SLOT+IUSE logic <<----
119
120 if tc_version_is_at_least 4.6 ; then
121         LICENSE="GPL-3+ LGPL-3+ || ( GPL-3+ libgcc libstdc++ gcc-runtime-library-exception-3.1 ) FDL-1.3+"
122 elif tc_version_is_at_least 4.4 ; then
123         LICENSE="GPL-3+ LGPL-3+ || ( GPL-3+ libgcc libstdc++ gcc-runtime-library-exception-3.1 ) FDL-1.2+"
124 elif tc_version_is_at_least 4.3 ; then
125         LICENSE="GPL-3+ LGPL-3+ || ( GPL-3+ libgcc libstdc++ ) FDL-1.2+"
126 elif tc_version_is_at_least 4.2 ; then
127         LICENSE="GPL-3+ LGPL-2.1+ || ( GPL-3+ libgcc libstdc++ ) FDL-1.2+"
128 elif tc_version_is_at_least 3.3 ; then
129         LICENSE="GPL-2+ LGPL-2.1+ FDL-1.2+"
130 else
131         LICENSE="GPL-2+ LGPL-2.1+ FDL-1.1+"
132 fi
133
134 IUSE="multislot regression-test vanilla"
135 IUSE_DEF=( nls nptl )
136
137 if [[ ${PN} != "kgcc64" && ${PN} != gcc-* ]] ; then
138         IUSE+=" altivec debug"
139         IUSE_DEF+=( cxx fortran )
140         [[ -n ${PIE_VER} ]] && IUSE+=" nopie"
141         [[ -n ${HTB_VER} ]] && IUSE+=" boundschecking"
142         [[ -n ${D_VER}   ]] && IUSE+=" d"
143         [[ -n ${SPECS_VER} ]] && IUSE+=" nossp"
144         tc_version_is_at_least 3 && IUSE+=" doc gcj awt hardened multilib objc"
145         tc_version_is_at_least 4.0 && IUSE+=" objc-gc"
146         tc_version_is_between 4.0 4.9 && IUSE+=" mudflap"
147         tc_version_is_at_least 4.1 && IUSE+=" libssp objc++"
148         tc_version_is_at_least 4.2 && IUSE_DEF+=( openmp )
149         tc_version_is_at_least 4.3 && IUSE+=" fixed-point"
150         tc_version_is_at_least 4.7 && IUSE+=" go"
151         # Note: while <=gcc-4.7 also supported graphite, it required forked ppl
152         # versions which we dropped.  Since graphite was also experimental in
153         # the older versions, we don't want to bother supporting it.  #448024
154         tc_version_is_at_least 4.8 && IUSE+=" graphite" IUSE_DEF+=( sanitize )
155         tc_version_is_at_least 4.9 && IUSE+=" cilk"
156         tc_version_is_at_least 5.0 && IUSE+=" jit"
157         tc_version_is_at_least 6.0 && IUSE+=" pie +ssp"
158 fi
159
160 IUSE+=" ${IUSE_DEF[*]/#/+}"
161
162 # Support upgrade paths here or people get pissed
163 if ! tc_version_is_at_least 4.8 || is_crosscompile || use multislot || [[ ${GCC_PV} == *_alpha* ]] ; then
164         SLOT="${GCC_CONFIG_VER}"
165 elif ! tc_version_is_at_least 5.0 ; then
166         SLOT="${GCC_BRANCH_VER}"
167 else
168         # Upstream changed versioning w/gcc-5+, so SLOT matches major only. #555164
169         SLOT="${GCCMAJOR}"
170 fi
171
172 #---->> DEPEND <<----
173
174 RDEPEND="sys-libs/zlib
175         nls? ( virtual/libintl )"
176
177 tc_version_is_at_least 3 && RDEPEND+=" virtual/libiconv"
178
179 if tc_version_is_at_least 4 ; then
180         GMP_MPFR_DEPS=">=dev-libs/gmp-4.3.2:0 >=dev-libs/mpfr-2.4.2:0"
181         if tc_version_is_at_least 4.3 ; then
182                 RDEPEND+=" ${GMP_MPFR_DEPS}"
183         elif in_iuse fortran ; then
184                 RDEPEND+=" fortran? ( ${GMP_MPFR_DEPS} )"
185         fi
186 fi
187
188 tc_version_is_at_least 4.5 && RDEPEND+=" >=dev-libs/mpc-0.8.1:0"
189
190 if in_iuse graphite ; then
191         if tc_version_is_at_least 5.0 ; then
192                 RDEPEND+=" graphite? ( >=dev-libs/isl-0.14 )"
193         elif tc_version_is_at_least 4.8 ; then
194                 RDEPEND+="
195                         graphite? (
196                                 >=dev-libs/cloog-0.18.0
197                                 >=dev-libs/isl-0.11.1
198                         )"
199         fi
200 fi
201
202 DEPEND="${RDEPEND}
203         >=sys-devel/bison-1.875
204         >=sys-devel/flex-2.5.4
205         nls? ( sys-devel/gettext )
206         regression-test? (
207                 >=dev-util/dejagnu-1.4.4
208                 >=sys-devel/autogen-5.5.4
209         )"
210
211 if in_iuse gcj ; then
212         GCJ_DEPS=">=media-libs/libart_lgpl-2.1"
213         GCJ_GTK_DEPS="
214                 x11-libs/libXt
215                 x11-libs/libX11
216                 x11-libs/libXtst
217                 x11-proto/xproto
218                 x11-proto/xextproto
219                 =x11-libs/gtk+-2*
220                 virtual/pkgconfig
221         "
222         tc_version_is_at_least 3.4 && GCJ_GTK_DEPS+=" x11-libs/pango"
223         tc_version_is_at_least 4.2 && GCJ_DEPS+=" app-arch/zip app-arch/unzip"
224         DEPEND+=" gcj? ( awt? ( ${GCJ_GTK_DEPS} ) ${GCJ_DEPS} )"
225 fi
226
227 PDEPEND=">=sys-devel/gcc-config-1.7"
228
229 #---->> S + SRC_URI essentials <<----
230
231 # Set the source directory depending on whether we're using
232 # a prerelease, snapshot, or release tarball.
233 S=$(
234         if [[ -n ${PRERELEASE} ]] ; then
235                 echo ${WORKDIR}/gcc-${PRERELEASE}
236         elif [[ -n ${SNAPSHOT} ]] ; then
237                 echo ${WORKDIR}/gcc-${SNAPSHOT}
238         else
239                 echo ${WORKDIR}/gcc-${GCC_RELEASE_VER}
240         fi
241 )
242
243 gentoo_urls() {
244         local devspace="HTTP~vapier/dist/URI HTTP~rhill/dist/URI
245         HTTP~zorry/patches/gcc/URI HTTP~blueness/dist/URI"
246         devspace=${devspace//HTTP/https:\/\/dev.gentoo.org\/}
247         echo mirror://gentoo/$1 ${devspace//URI/$1}
248 }
249
250 # This function handles the basics of setting the SRC_URI for a gcc ebuild.
251 # To use, set SRC_URI with:
252 #
253 #       SRC_URI="$(get_gcc_src_uri)"
254 #
255 # Other than the variables normally set by portage, this function's behavior
256 # can be altered by setting the following:
257 #
258 #       SNAPSHOT
259 #                       If set, this variable signals that we should be using a snapshot of
260 #                       gcc. It is expected to be in the format "YYYY-MM-DD". Note that if
261 #                       the ebuild has a _pre suffix, this variable is ignored and the
262 #                       prerelease tarball is used instead.
263 #
264 #       BRANCH_UPDATE
265 #                       If set, this variable signals that we should be using the main
266 #                       release tarball (determined by ebuild version) and applying a
267 #                       CVS branch update patch against it. The location of this branch
268 #                       update patch is assumed to be in ${GENTOO_TOOLCHAIN_BASE_URI}.
269 #                       Just like with SNAPSHOT, this variable is ignored if the ebuild
270 #                       has a _pre suffix.
271 #
272 #       PATCH_VER
273 #       PATCH_GCC_VER
274 #                       This should be set to the version of the gentoo patch tarball.
275 #                       The resulting filename of this tarball will be:
276 #                       gcc-${PATCH_GCC_VER:-${GCC_RELEASE_VER}}-patches-${PATCH_VER}.tar.bz2
277 #
278 #       PIE_VER
279 #       PIE_GCC_VER
280 #                       These variables control patching in various updates for the logic
281 #                       controlling Position Independant Executables. PIE_VER is expected
282 #                       to be the version of this patch, and PIE_GCC_VER the gcc version of
283 #                       the patch:
284 #                       An example:
285 #                                       PIE_VER="8.7.6.5"
286 #                                       PIE_GCC_VER="3.4.0"
287 #                       The resulting filename of this tarball will be:
288 #                       gcc-${PIE_GCC_VER:-${GCC_RELEASE_VER}}-piepatches-v${PIE_VER}.tar.bz2
289 #
290 #       SPECS_VER
291 #       SPECS_GCC_VER
292 #                       This is for the minispecs files included in the hardened gcc-4.x
293 #                       The specs files for hardenedno*, vanilla and for building the "specs" file.
294 #                       SPECS_VER is expected to be the version of this patch, SPECS_GCC_VER
295 #                       the gcc version of the patch.
296 #                       An example:
297 #                                       SPECS_VER="8.7.6.5"
298 #                                       SPECS_GCC_VER="3.4.0"
299 #                       The resulting filename of this tarball will be:
300 #                       gcc-${SPECS_GCC_VER:-${GCC_RELEASE_VER}}-specs-${SPECS_VER}.tar.bz2
301 #
302 #       HTB_VER
303 #       HTB_GCC_VER
304 #                       These variables control whether or not an ebuild supports Herman
305 #                       ten Brugge's bounds-checking patches. If you want to use a patch
306 #                       for an older gcc version with a new gcc, make sure you set
307 #                       HTB_GCC_VER to that version of gcc.
308 get_gcc_src_uri() {
309         export PATCH_GCC_VER=${PATCH_GCC_VER:-${GCC_RELEASE_VER}}
310         export UCLIBC_GCC_VER=${UCLIBC_GCC_VER:-${PATCH_GCC_VER}}
311         export PIE_GCC_VER=${PIE_GCC_VER:-${GCC_RELEASE_VER}}
312         export HTB_GCC_VER=${HTB_GCC_VER:-${GCC_RELEASE_VER}}
313         export SPECS_GCC_VER=${SPECS_GCC_VER:-${GCC_RELEASE_VER}}
314
315         # Set where to download gcc itself depending on whether we're using a
316         # prerelease, snapshot, or release tarball.
317         if [[ ${PV} == *9999* ]] ; then
318                 # Nothing to do w/git snapshots.
319                 :
320         elif [[ -n ${PRERELEASE} ]] ; then
321                 GCC_SRC_URI="ftp://gcc.gnu.org/pub/gcc/prerelease-${PRERELEASE}/gcc-${PRERELEASE}.tar.bz2"
322         elif [[ -n ${SNAPSHOT} ]] ; then
323                 GCC_SRC_URI="ftp://gcc.gnu.org/pub/gcc/snapshots/${SNAPSHOT}/gcc-${SNAPSHOT}.tar.bz2"
324         else
325                 GCC_SRC_URI="mirror://gnu/gcc/gcc-${GCC_PV}/gcc-${GCC_RELEASE_VER}.tar.bz2"
326                 # we want all branch updates to be against the main release
327                 [[ -n ${BRANCH_UPDATE} ]] && \
328                         GCC_SRC_URI+=" $(gentoo_urls gcc-${GCC_RELEASE_VER}-branch-update-${BRANCH_UPDATE}.patch.bz2)"
329         fi
330
331         [[ -n ${UCLIBC_VER} ]] && \
332                 GCC_SRC_URI+=" $(gentoo_urls gcc-${UCLIBC_GCC_VER}-uclibc-patches-${UCLIBC_VER}.tar.bz2)"
333         [[ -n ${PATCH_VER} ]] && \
334                 GCC_SRC_URI+=" $(gentoo_urls gcc-${PATCH_GCC_VER}-patches-${PATCH_VER}.tar.bz2)"
335
336         # strawberry pie, Cappuccino and a Gauloises (it's a good thing)
337         [[ -n ${PIE_VER} ]] && \
338                 PIE_CORE=${PIE_CORE:-gcc-${PIE_GCC_VER}-piepatches-v${PIE_VER}.tar.bz2} && \
339                 GCC_SRC_URI+=" $(gentoo_urls ${PIE_CORE})"
340
341         # gcc minispec for the hardened gcc 4 compiler
342         [[ -n ${SPECS_VER} ]] && \
343                 GCC_SRC_URI+=" $(gentoo_urls gcc-${SPECS_GCC_VER}-specs-${SPECS_VER}.tar.bz2)"
344
345         # gcc bounds checking patch
346         if [[ -n ${HTB_VER} ]] ; then
347                 local HTBFILE="bounds-checking-gcc-${HTB_GCC_VER}-${HTB_VER}.patch.bz2"
348                 GCC_SRC_URI+="
349                         boundschecking? (
350                                 mirror://sourceforge/boundschecking/${HTBFILE}
351                                 $(gentoo_urls ${HTBFILE})
352                         )"
353         fi
354
355         [[ -n ${D_VER} ]] && \
356                 GCC_SRC_URI+=" d? ( mirror://sourceforge/dgcc/gdc-${D_VER}-src.tar.bz2 )"
357
358         if in_iuse gcj ; then
359                 if tc_version_is_at_least 4.5 ; then
360                         GCC_SRC_URI+=" gcj? ( ftp://sourceware.org/pub/java/ecj-4.5.jar )"
361                 elif tc_version_is_at_least 4.3 ; then
362                         GCC_SRC_URI+=" gcj? ( ftp://sourceware.org/pub/java/ecj-4.3.jar )"
363                 fi
364         fi
365
366         echo "${GCC_SRC_URI}"
367 }
368
369 SRC_URI=$(get_gcc_src_uri)
370
371 #---->> pkg_pretend <<----
372
373 toolchain_pkg_pretend() {
374         if [[ -n ${PRERELEASE}${SNAPSHOT} || ${PV} == *9999* ]] &&
375            [[ -z ${I_PROMISE_TO_SUPPLY_PATCHES_WITH_BUGS} ]] ; then
376                 die "Please \`export I_PROMISE_TO_SUPPLY_PATCHES_WITH_BUGS=1\` or define it" \
377                         "in your make.conf if you want to use this version."
378         fi
379
380         [[ -z ${UCLIBC_VER} ]] && [[ ${CTARGET} == *-uclibc* ]] && \
381                 die "Sorry, this version does not support uClibc"
382
383         if ! use_if_iuse cxx ; then
384                 use_if_iuse go && ewarn 'Go requires a C++ compiler, disabled due to USE="-cxx"'
385                 use_if_iuse objc++ && ewarn 'Obj-C++ requires a C++ compiler, disabled due to USE="-cxx"'
386                 use_if_iuse gcj && ewarn 'GCJ requires a C++ compiler, disabled due to USE="-cxx"'
387         fi
388
389         want_minispecs
390 }
391
392 #---->> pkg_setup <<----
393
394 toolchain_pkg_setup() {
395         case ${EAPI} in
396         2|3) toolchain_pkg_pretend ;;
397         esac
398
399         # we dont want to use the installed compiler's specs to build gcc
400         unset GCC_SPECS
401         unset LANGUAGES #265283
402 }
403
404 #---->> src_unpack <<----
405
406 toolchain_src_unpack() {
407         if [[ ${PV} == *9999* ]]; then
408                 git-2_src_unpack
409         else
410                 gcc_quick_unpack
411         fi
412 }
413
414 gcc_quick_unpack() {
415         pushd "${WORKDIR}" > /dev/null
416         export PATCH_GCC_VER=${PATCH_GCC_VER:-${GCC_RELEASE_VER}}
417         export UCLIBC_GCC_VER=${UCLIBC_GCC_VER:-${PATCH_GCC_VER}}
418         export PIE_GCC_VER=${PIE_GCC_VER:-${GCC_RELEASE_VER}}
419         export HTB_GCC_VER=${HTB_GCC_VER:-${GCC_RELEASE_VER}}
420         export SPECS_GCC_VER=${SPECS_GCC_VER:-${GCC_RELEASE_VER}}
421
422         if [[ -n ${GCC_A_FAKEIT} ]] ; then
423                 unpack ${GCC_A_FAKEIT}
424         elif [[ -n ${PRERELEASE} ]] ; then
425                 unpack gcc-${PRERELEASE}.tar.bz2
426         elif [[ -n ${SNAPSHOT} ]] ; then
427                 unpack gcc-${SNAPSHOT}.tar.bz2
428         elif [[ ${PV} != *9999* ]] ; then
429                 unpack gcc-${GCC_RELEASE_VER}.tar.bz2
430                 # We want branch updates to be against a release tarball
431                 if [[ -n ${BRANCH_UPDATE} ]] ; then
432                         pushd "${S}" > /dev/null
433                         epatch "${DISTDIR}"/gcc-${GCC_RELEASE_VER}-branch-update-${BRANCH_UPDATE}.patch.bz2
434                         popd > /dev/null
435                 fi
436         fi
437
438         if [[ -n ${D_VER} ]] && use d ; then
439                 pushd "${S}"/gcc > /dev/null
440                 unpack gdc-${D_VER}-src.tar.bz2
441                 cd ..
442                 ebegin "Adding support for the D language"
443                 ./gcc/d/setup-gcc.sh >& "${T}"/dgcc.log
444                 if ! eend $? ; then
445                         eerror "The D GCC package failed to apply"
446                         eerror "Please include this log file when posting a bug report:"
447                         eerror "  ${T}/dgcc.log"
448                         die "failed to include the D language"
449                 fi
450                 popd > /dev/null
451         fi
452
453         [[ -n ${PATCH_VER} ]] && \
454                 unpack gcc-${PATCH_GCC_VER}-patches-${PATCH_VER}.tar.bz2
455
456         [[ -n ${UCLIBC_VER} ]] && \
457                 unpack gcc-${UCLIBC_GCC_VER}-uclibc-patches-${UCLIBC_VER}.tar.bz2
458
459         if want_pie ; then
460                 if [[ -n ${PIE_CORE} ]] ; then
461                         unpack ${PIE_CORE}
462                 else
463                         unpack gcc-${PIE_GCC_VER}-piepatches-v${PIE_VER}.tar.bz2
464                 fi
465                 [[ -n ${SPECS_VER} ]] && \
466                         unpack gcc-${SPECS_GCC_VER}-specs-${SPECS_VER}.tar.bz2
467         fi
468
469         use_if_iuse boundschecking && unpack "bounds-checking-gcc-${HTB_GCC_VER}-${HTB_VER}.patch.bz2"
470
471         popd > /dev/null
472 }
473
474 #---->> src_prepare <<----
475
476 toolchain_src_prepare() {
477         export BRANDING_GCC_PKGVERSION="Gentoo ${GCC_PVR}"
478         cd "${S}"
479
480         if ! use vanilla ; then
481                 if [[ -n ${PATCH_VER} ]] ; then
482                         guess_patch_type_in_dir "${WORKDIR}"/patch
483                         EPATCH_MULTI_MSG="Applying Gentoo patches ..." \
484                         epatch "${WORKDIR}"/patch
485                         BRANDING_GCC_PKGVERSION="${BRANDING_GCC_PKGVERSION} p${PATCH_VER}"
486                 fi
487                 if [[ -n ${UCLIBC_VER} ]] ; then
488                         guess_patch_type_in_dir "${WORKDIR}"/uclibc
489                         EPATCH_MULTI_MSG="Applying uClibc patches ..." \
490                         epatch "${WORKDIR}"/uclibc
491                 fi
492         fi
493         do_gcc_HTB_patches
494         do_gcc_PIE_patches
495         epatch_user
496
497         if ( tc_version_is_at_least 4.8.2 || use hardened ) && ! use vanilla ; then
498                 make_gcc_hard
499         fi
500
501         # install the libstdc++ python into the right location
502         # http://gcc.gnu.org/PR51368
503         if tc_version_is_between 4.5 4.7 ; then
504                 sed -i \
505                         '/^pythondir =/s:=.*:= $(datadir)/python:' \
506                         "${S}"/libstdc++-v3/python/Makefile.in || die
507         fi
508
509         # make sure the pkg config files install into multilib dirs.
510         # since we configure with just one --libdir, we can't use that
511         # (as gcc itself takes care of building multilibs).  #435728
512         find "${S}" -name Makefile.in \
513                 -exec sed -i '/^pkgconfigdir/s:=.*:=$(toolexeclibdir)/pkgconfig:' {} +
514
515         # No idea when this first started being fixed, but let's go with 4.3.x for now
516         if ! tc_version_is_at_least 4.3 ; then
517                 fix_files=""
518                 for x in contrib/test_summary libstdc++-v3/scripts/check_survey.in ; do
519                         [[ -e ${x} ]] && fix_files="${fix_files} ${x}"
520                 done
521                 ht_fix_file ${fix_files} */configure *.sh */Makefile.in
522         fi
523
524         setup_multilib_osdirnames
525         gcc_version_patch
526
527         if tc_version_is_at_least 4.1 ; then
528                 if [[ -n ${SNAPSHOT} || -n ${PRERELEASE} ]] ; then
529                         # BASE-VER must be a three-digit version number
530                         # followed by an optional -pre string
531                         #   eg. 4.5.1, 4.6.2-pre20120213, 4.7.0-pre9999
532                         # If BASE-VER differs from ${PV/_/-} then libraries get installed in
533                         # the wrong directory.
534                         echo ${PV/_/-} > "${S}"/gcc/BASE-VER
535                 fi
536         fi
537
538         # >= gcc-4.3 doesn't bundle ecj.jar, so copy it
539         if tc_version_is_at_least 4.3 && use gcj ; then
540                 if tc_version_is_at_least 4.5 ; then
541                         einfo "Copying ecj-4.5.jar"
542                         cp -pPR "${DISTDIR}/ecj-4.5.jar" "${S}/ecj.jar" || die
543                 else
544                         einfo "Copying ecj-4.3.jar"
545                         cp -pPR "${DISTDIR}/ecj-4.3.jar" "${S}/ecj.jar" || die
546                 fi
547         fi
548
549         # disable --as-needed from being compiled into gcc specs
550         # natively when using a gcc version < 3.4.4
551         # http://gcc.gnu.org/PR14992
552         if ! tc_version_is_at_least 3.4.4 ; then
553                 sed -i -e s/HAVE_LD_AS_NEEDED/USE_LD_AS_NEEDED/g "${S}"/gcc/config.in
554         fi
555
556         # In gcc 3.3.x and 3.4.x, rename the java bins to gcc-specific names
557         # in line with gcc-4.
558         if tc_version_is_between 3.3 4.0 ; then
559                 do_gcc_rename_java_bins
560         fi
561
562         # Prevent libffi from being installed
563         if tc_version_is_between 3.0 4.8 ; then
564                 sed -i -e 's/\(install.*:\) install-.*recursive/\1/' "${S}"/libffi/Makefile.in || die
565                 sed -i -e 's/\(install-data-am:\).*/\1/' "${S}"/libffi/include/Makefile.in || die
566         fi
567
568         # Fixup libtool to correctly generate .la files with portage
569         elibtoolize --portage --shallow --no-uclibc
570
571         gnuconfig_update
572
573         # update configure files
574         local f
575         einfo "Fixing misc issues in configure files"
576         for f in $(grep -l 'autoconf version 2.13' $(find "${S}" -name configure)) ; do
577                 ebegin "  Updating ${f/${S}\/} [LANG]"
578                 patch "${f}" "${GCC_FILESDIR}"/gcc-configure-LANG.patch >& "${T}"/configure-patch.log \
579                         || eerror "Please file a bug about this"
580                 eend $?
581         done
582         sed -i 's|A-Za-z0-9|[:alnum:]|g' "${S}"/gcc/*.awk #215828
583
584         # Prevent new texinfo from breaking old versions (see #198182, #464008)
585         tc_version_is_at_least 4.1 && epatch "${GCC_FILESDIR}"/gcc-configure-texinfo.patch
586
587         if [[ -x contrib/gcc_update ]] ; then
588                 einfo "Touching generated files"
589                 ./contrib/gcc_update --touch | \
590                         while read f ; do
591                                 einfo "  ${f%%...}"
592                         done
593         fi
594 }
595
596 guess_patch_type_in_dir() {
597         [[ -n $(ls "$1"/*.bz2 2>/dev/null) ]] \
598                 && EPATCH_SUFFIX="patch.bz2" \
599                 || EPATCH_SUFFIX="patch"
600 }
601
602 do_gcc_HTB_patches() {
603         use_if_iuse boundschecking || return 0
604
605         # modify the bounds checking patch with a regression patch
606         epatch "${WORKDIR}/bounds-checking-gcc-${HTB_GCC_VER}-${HTB_VER}.patch"
607         BRANDING_GCC_PKGVERSION="${BRANDING_GCC_PKGVERSION}, HTB-${HTB_GCC_VER}-${HTB_VER}"
608 }
609
610 do_gcc_PIE_patches() {
611         want_pie || return 0
612         use vanilla && return 0
613
614         if tc_version_is_at_least 4.3.2 ; then
615                 guess_patch_type_in_dir "${WORKDIR}"/piepatch/
616                 EPATCH_MULTI_MSG="Applying pie patches ..." \
617                 epatch "${WORKDIR}"/piepatch/
618         else
619                 guess_patch_type_in_dir "${WORKDIR}"/piepatch/upstream
620
621                 # corrects startfile/endfile selection and shared/static/pie flag usage
622                 EPATCH_MULTI_MSG="Applying upstream pie patches ..." \
623                 epatch "${WORKDIR}"/piepatch/upstream
624                 # adds non-default pie support (rs6000)
625                 EPATCH_MULTI_MSG="Applying non-default pie patches ..." \
626                 epatch "${WORKDIR}"/piepatch/nondef
627                 # adds default pie support (rs6000 too) if DEFAULT_PIE[_SSP] is defined
628                 EPATCH_MULTI_MSG="Applying default pie patches ..." \
629                 epatch "${WORKDIR}"/piepatch/def
630         fi
631
632         BRANDING_GCC_PKGVERSION="${BRANDING_GCC_PKGVERSION}, pie-${PIE_VER}"
633 }
634
635 # configure to build with the hardened GCC specs as the default
636 make_gcc_hard() {
637         # we want to be able to control the pie patch logic via something other
638         # than ALL_CFLAGS...
639         sed -e '/^ALL_CFLAGS/iHARD_CFLAGS = ' \
640                 -e 's|^ALL_CFLAGS = |ALL_CFLAGS = $(HARD_CFLAGS) |' \
641                 -i "${S}"/gcc/Makefile.in
642         # Need to add HARD_CFLAGS to ALL_CXXFLAGS on >= 4.7
643         if tc_version_is_at_least 4.7 ; then
644                 sed -e '/^ALL_CXXFLAGS/iHARD_CFLAGS = ' \
645                         -e 's|^ALL_CXXFLAGS = |ALL_CXXFLAGS = $(HARD_CFLAGS) |' \
646                         -i "${S}"/gcc/Makefile.in
647         fi
648
649         # defaults to enable for all toolchains
650         local gcc_hard_flags=""
651         if use hardened ; then
652                 if hardened_gcc_works ; then
653                         einfo "Updating gcc to use automatic PIE + SSP building ..."
654                         gcc_hard_flags+=" -DEFAULT_PIE_SSP"
655                 elif hardened_gcc_works pie ; then
656                         einfo "Updating gcc to use automatic PIE building ..."
657                         ewarn "SSP has not been enabled by default"
658                         gcc_hard_flags+=" -DEFAULT_PIE"
659                 elif hardened_gcc_works ssp ; then
660                         einfo "Updating gcc to use automatic SSP building ..."
661                         ewarn "PIE has not been enabled by default"
662                         gcc_hard_flags+=" -DEFAULT_SSP"
663                 else
664                         # do nothing if hardened isn't supported, but don't die either
665                         ewarn "hardened is not supported for this arch in this gcc version"
666                         return 0
667                 fi
668                 # rebrand to make bug reports easier
669                 BRANDING_GCC_PKGVERSION=${BRANDING_GCC_PKGVERSION/Gentoo/Gentoo Hardened}
670         else
671                 if hardened_gcc_works ssp ; then
672                         einfo "Updating gcc to use automatic SSP building ..."
673                         gcc_hard_flags+=" -DEFAULT_SSP"
674                 fi
675         fi
676
677         sed -i \
678                 -e "/^HARD_CFLAGS = /s|=|= ${gcc_hard_flags} |" \
679                 "${S}"/gcc/Makefile.in || die
680
681 }
682
683 # This is a historical wart.  The original Gentoo/amd64 port used:
684 #    lib32 - 32bit binaries (x86)
685 #    lib64 - 64bit binaries (x86_64)
686 #    lib   - "native" binaries (a symlink to lib64)
687 # Most other distros use the logic (including mainline gcc):
688 #    lib   - 32bit binaries (x86)
689 #    lib64 - 64bit binaries (x86_64)
690 # Over time, Gentoo is migrating to the latter form.
691 #
692 # Unfortunately, due to distros picking the lib32 behavior, newer gcc
693 # versions will dynamically detect whether to use lib or lib32 for its
694 # 32bit multilib.  So, to keep the automagic from getting things wrong
695 # while people are transitioning from the old style to the new style,
696 # we always set the MULTILIB_OSDIRNAMES var for relevant targets.
697 setup_multilib_osdirnames() {
698         is_multilib || return 0
699
700         local config
701         local libdirs="../lib64 ../lib32"
702
703         # this only makes sense for some Linux targets
704         case ${CTARGET} in
705         x86_64*-linux*)    config="i386" ;;
706         powerpc64*-linux*) config="rs6000" ;;
707         sparc64*-linux*)   config="sparc" ;;
708         s390x*-linux*)     config="s390" ;;
709         *)                     return 0 ;;
710         esac
711         config+="/t-linux64"
712
713         local sed_args=()
714         if tc_version_is_at_least 4.6 ; then
715                 sed_args+=( -e 's:$[(]call if_multiarch[^)]*[)]::g' )
716         fi
717         if [[ ${SYMLINK_LIB} == "yes" ]] ; then
718                 einfo "updating multilib directories to be: ${libdirs}"
719                 if tc_version_is_at_least 4.6.4 || tc_version_is_at_least 4.7 ; then
720                         sed_args+=( -e '/^MULTILIB_OSDIRNAMES.*lib32/s:[$][(]if.*):../lib32:' )
721                 else
722                         sed_args+=( -e "/^MULTILIB_OSDIRNAMES/s:=.*:= ${libdirs}:" )
723                 fi
724         else
725                 einfo "using upstream multilib; disabling lib32 autodetection"
726                 sed_args+=( -r -e 's:[$][(]if.*,(.*)[)]:\1:' )
727         fi
728         sed -i "${sed_args[@]}" "${S}"/gcc/config/${config} || die
729 }
730
731 gcc_version_patch() {
732         # gcc-4.3+ has configure flags (whoo!)
733         tc_version_is_at_least 4.3 && return 0
734
735         local version_string=${GCC_CONFIG_VER}
736         [[ -n ${BRANCH_UPDATE} ]] && version_string+=" ${BRANCH_UPDATE}"
737
738         einfo "patching gcc version: ${version_string} (${BRANDING_GCC_PKGVERSION})"
739
740         local gcc_sed=( -e 's:gcc\.gnu\.org/bugs\.html:bugs\.gentoo\.org/:' )
741         if grep -qs VERSUFFIX "${S}"/gcc/version.c ; then
742                 gcc_sed+=( -e "/VERSUFFIX \"\"/s:\"\":\" (${BRANDING_GCC_PKGVERSION})\":" )
743         else
744                 version_string="${version_string} (${BRANDING_GCC_PKGVERSION})"
745                 gcc_sed+=( -e "/const char version_string\[\] = /s:= \".*\":= \"${version_string}\":" )
746         fi
747         sed -i "${gcc_sed[@]}" "${S}"/gcc/version.c || die
748 }
749
750 do_gcc_rename_java_bins() {
751         # bug #139918 - conflict between gcc and java-config-2 for ownership of
752         # /usr/bin/rmi{c,registry}.      Done with mv & sed rather than a patch
753         # because patches would be large (thanks to the rename of man files),
754         # and it's clear from the sed invocations that all that changes is the
755         # rmi{c,registry} names to grmi{c,registry} names.
756         # Kevin F. Quinn 2006-07-12
757         einfo "Renaming jdk executables rmic and rmiregistry to grmic and grmiregistry."
758         # 1) Move the man files if present (missing prior to gcc-3.4)
759         for manfile in rmic rmiregistry ; do
760                 [[ -f ${S}/gcc/doc/${manfile}.1 ]] || continue
761                 mv "${S}"/gcc/doc/${manfile}.1 "${S}"/gcc/doc/g${manfile}.1
762         done
763         # 2) Fixup references in the docs if present (mission prior to gcc-3.4)
764         for jfile in gcc/doc/gcj.info gcc/doc/grmic.1 gcc/doc/grmiregistry.1 gcc/java/gcj.texi ; do
765                 [[ -f ${S}/${jfile} ]] || continue
766                 sed -i -e 's:rmiregistry:grmiregistry:g' "${S}"/${jfile} ||
767                         die "Failed to fixup file ${jfile} for rename to grmiregistry"
768                 sed -i -e 's:rmic:grmic:g' "${S}"/${jfile} ||
769                         die "Failed to fixup file ${jfile} for rename to grmic"
770         done
771         # 3) Fixup Makefiles to build the changed executable names
772         #        These are present in all 3.x versions, and are the important bit
773         #        to get gcc to build with the new names.
774         for jfile in libjava/Makefile.am libjava/Makefile.in gcc/java/Make-lang.in ; do
775                 sed -i -e 's:rmiregistry:grmiregistry:g' "${S}"/${jfile} ||
776                         die "Failed to fixup file ${jfile} for rename to grmiregistry"
777                 # Careful with rmic on these files; it's also the name of a directory
778                 # which should be left unchanged.  Replace occurrences of 'rmic$',
779                 # 'rmic_' and 'rmic '.
780                 sed -i -e 's:rmic\([$_ ]\):grmic\1:g' "${S}"/${jfile} ||
781                         die "Failed to fixup file ${jfile} for rename to grmic"
782         done
783 }
784
785 #---->> src_configure <<----
786
787 toolchain_src_configure() {
788         downgrade_arch_flags
789         gcc_do_filter_flags
790
791         einfo "CFLAGS=\"${CFLAGS}\""
792         einfo "CXXFLAGS=\"${CXXFLAGS}\""
793         einfo "LDFLAGS=\"${LDFLAGS}\""
794
795         # Force internal zip based jar script to avoid random
796         # issues with 3rd party jar implementations.  #384291
797         export JAR=no
798
799         # For hardened gcc 4.3 piepatchset to build the hardened specs
800         # file (build.specs) to use when building gcc.
801         if ! tc_version_is_at_least 4.4 && want_minispecs ; then
802                 setup_minispecs_gcc_build_specs
803         fi
804
805         local confgcc=( --host=${CHOST} )
806
807         if is_crosscompile || tc-is-cross-compiler ; then
808                 # Straight from the GCC install doc:
809                 # "GCC has code to correctly determine the correct value for target
810                 # for nearly all native systems. Therefore, we highly recommend you
811                 # not provide a configure target when configuring a native compiler."
812                 confgcc+=( --target=${CTARGET} )
813         fi
814         [[ -n ${CBUILD} ]] && confgcc+=( --build=${CBUILD} )
815
816         confgcc+=(
817                 --prefix="${PREFIX}"
818                 --bindir="${BINPATH}"
819                 --includedir="${INCLUDEPATH}"
820                 --datadir="${DATAPATH}"
821                 --mandir="${DATAPATH}/man"
822                 --infodir="${DATAPATH}/info"
823                 --with-gxx-include-dir="${STDCXX_INCDIR}"
824         )
825
826         # Stick the python scripts in their own slotted directory (bug #279252)
827         #
828         #  --with-python-dir=DIR
829         #  Specifies where to install the Python modules used for aot-compile. DIR
830         #  should not include the prefix used in installation. For example, if the
831         #  Python modules are to be installed in /usr/lib/python2.5/site-packages,
832         #  then --with-python-dir=/lib/python2.5/site-packages should be passed.
833         #
834         # This should translate into "/share/gcc-data/${CTARGET}/${GCC_CONFIG_VER}/python"
835         if tc_version_is_at_least 4.4 ; then
836                 confgcc+=( --with-python-dir=${DATAPATH/$PREFIX/}/python )
837         fi
838
839         ### language options
840
841         local GCC_LANG="c"
842         is_cxx && GCC_LANG+=",c++"
843         is_d   && GCC_LANG+=",d"
844         is_gcj && GCC_LANG+=",java"
845         is_go  && GCC_LANG+=",go"
846         is_jit && GCC_LANG+=",jit"
847         if is_objc || is_objcxx ; then
848                 GCC_LANG+=",objc"
849                 if tc_version_is_at_least 4 ; then
850                         use objc-gc && confgcc+=( --enable-objc-gc )
851                 fi
852                 is_objcxx && GCC_LANG+=",obj-c++"
853         fi
854
855         # fortran support just got sillier! the lang value can be f77 for
856         # fortran77, f95 for fortran95, or just plain old fortran for the
857         # currently supported standard depending on gcc version.
858         is_fortran && GCC_LANG+=",fortran"
859         is_f77 && GCC_LANG+=",f77"
860         is_f95 && GCC_LANG+=",f95"
861
862         # We do NOT want 'ADA support' in here!
863         # is_ada && GCC_LANG+=",ada"
864
865         confgcc+=( --enable-languages=${GCC_LANG} )
866
867         ### general options
868
869         confgcc+=(
870                 --enable-obsolete
871                 --enable-secureplt
872                 --disable-werror
873                 --with-system-zlib
874         )
875
876         if use nls ; then
877                 confgcc+=( --enable-nls --without-included-gettext )
878         else
879                 confgcc+=( --disable-nls )
880         fi
881
882         tc_version_is_at_least 3.4 || confgcc+=( --disable-libunwind-exceptions )
883
884         # Use the default ("release") checking because upstream usually neglects
885         # to test "disabled" so it has a history of breaking. #317217
886         if tc_version_is_at_least 3.4 ; then
887                 # The "release" keyword is new to 4.0. #551636
888                 local off=$(tc_version_is_at_least 4.0 && echo release || echo no)
889                 confgcc+=( --enable-checking="${GCC_CHECKS_LIST:-$(usex debug yes ${off})}" )
890         fi
891
892         # Branding
893         tc_version_is_at_least 4.3 && confgcc+=(
894                 --with-bugurl=https://bugs.gentoo.org/
895                 --with-pkgversion="${BRANDING_GCC_PKGVERSION}"
896         )
897
898         # If we want hardened support with the newer piepatchset for >=gcc 4.4
899         if tc_version_is_at_least 4.4 && want_minispecs ; then
900                 confgcc+=( $(use_enable hardened esp) )
901         fi
902
903         # allow gcc to search for clock funcs in the main C lib.
904         # if it can't find them, then tough cookies -- we aren't
905         # going to link in -lrt to all C++ apps.  #411681
906         if tc_version_is_at_least 4.4 && is_cxx ; then
907                 confgcc+=( --enable-libstdcxx-time )
908         fi
909
910         # The jit language requires this.
911         is_jit && confgcc+=( --enable-host-shared )
912
913         # # Turn on the -Wl,--build-id flag by default for ELF targets. #525942
914         # # This helps with locating debug files.
915         # case ${CTARGET} in
916         # *-linux-*|*-elf|*-eabi)
917         #       tc_version_is_at_least 4.5 && confgcc+=(
918         #               --enable-linker-build-id
919         #       )
920         #       ;;
921         # esac
922
923         # newer gcc versions like to bootstrap themselves with C++,
924         # so we need to manually disable it ourselves
925         if tc_version_is_between 4.7 4.8 && ! is_cxx ; then
926                 confgcc+=( --disable-build-with-cxx --disable-build-poststage1-with-cxx )
927         fi
928
929         ### Cross-compiler options
930         if is_crosscompile ; then
931                 # Enable build warnings by default with cross-compilers when system
932                 # paths are included (e.g. via -I flags).
933                 confgcc+=( --enable-poison-system-directories )
934
935                 # When building a stage1 cross-compiler (just C compiler), we have to
936                 # disable a bunch of features or gcc goes boom
937                 local needed_libc=""
938                 case ${CTARGET} in
939                 *-linux)                 needed_libc=no-fucking-clue;;
940                 *-dietlibc)              needed_libc=dietlibc;;
941                 *-elf|*-eabi)    needed_libc=newlib;;
942                 *-freebsd*)              needed_libc=freebsd-lib;;
943                 *-gnu*)                  needed_libc=glibc;;
944                 *-klibc)                 needed_libc=klibc;;
945                 *-musl*)                 needed_libc=musl;;
946                 *-uclibc*)
947                         if ! echo '#include <features.h>' | \
948                            $(tc-getCPP ${CTARGET}) -E -dD - 2>/dev/null | \
949                            grep -q __HAVE_SHARED__
950                         then #291870
951                                 confgcc+=( --disable-shared )
952                         fi
953                         needed_libc=uclibc
954                         ;;
955                 *-cygwin)                needed_libc=cygwin;;
956                 x86_64-*-mingw*|\
957                 *-w64-mingw*)    needed_libc=mingw64-runtime;;
958                 mingw*|*-mingw*) needed_libc=mingw-runtime;;
959                 avr)                     confgcc+=( --enable-shared --disable-threads );;
960                 esac
961                 if [[ -n ${needed_libc} ]] ; then
962                         local confgcc_no_libc=( --disable-shared )
963                         tc_version_is_at_least 4.8 && confgcc_no_libc+=( --disable-libatomic )
964                         if ! has_version ${CATEGORY}/${needed_libc} ; then
965                                 confgcc+=(
966                                         "${confgcc_no_libc[@]}"
967                                         --disable-threads
968                                         --without-headers
969                                 )
970                         elif built_with_use --hidden --missing false ${CATEGORY}/${needed_libc} crosscompile_opts_headers-only ; then
971                                 confgcc+=(
972                                         "${confgcc_no_libc[@]}"
973                                         --with-sysroot=${PREFIX}/${CTARGET}
974                                 )
975                         else
976                                 confgcc+=( --with-sysroot=${PREFIX}/${CTARGET} )
977                         fi
978                 fi
979
980                 tc_version_is_at_least 4.2 && confgcc+=( --disable-bootstrap )
981         else
982                 if tc-is-static-only ; then
983                         confgcc+=( --disable-shared )
984                 else
985                         confgcc+=( --enable-shared )
986                 fi
987                 case ${CHOST} in
988                 mingw*|*-mingw*|*-cygwin)
989                         confgcc+=( --enable-threads=win32 ) ;;
990                 *)
991                         confgcc+=( --enable-threads=posix ) ;;
992                 esac
993         fi
994
995         # __cxa_atexit is "essential for fully standards-compliant handling of
996         # destructors", but apparently requires glibc.
997         case ${CTARGET} in
998         *-uclibc*)
999                 confgcc+=(
1000                         --disable-__cxa_atexit
1001                         $(use_enable nptl tls)
1002                 )
1003                 tc_version_is_between 3.3 3.4 && confgcc+=( --enable-sjlj-exceptions )
1004                 if tc_version_is_between 3.4 4.3 ; then
1005                         confgcc+=( --enable-clocale=uclibc )
1006                 fi
1007                 ;;
1008         *-elf|*-eabi)
1009                 confgcc+=( --with-newlib )
1010                 ;;
1011         *-gnu*)
1012                 confgcc+=(
1013                         --enable-__cxa_atexit
1014                         --enable-clocale=gnu
1015                 )
1016                 ;;
1017         *-freebsd*)
1018                 confgcc+=( --enable-__cxa_atexit )
1019                 ;;
1020         *-solaris*)
1021                 confgcc+=( --enable-__cxa_atexit )
1022                 ;;
1023         esac
1024
1025         ### arch options
1026
1027         gcc-multilib-configure
1028
1029         # ppc altivec support
1030         confgcc+=( $(use_enable altivec) )
1031
1032         # gcc has fixed-point arithmetic support in 4.3 for mips targets that can
1033         # significantly increase compile time by several hours.  This will allow
1034         # users to control this feature in the event they need the support.
1035         tc_version_is_at_least 4.3 && confgcc+=( $(use_enable fixed-point) )
1036
1037         case $(tc-is-softfloat) in
1038         yes)    confgcc+=( --with-float=soft ) ;;
1039         softfp) confgcc+=( --with-float=softfp ) ;;
1040         *)
1041                 # If they've explicitly opt-ed in, do hardfloat,
1042                 # otherwise let the gcc default kick in.
1043                 case ${CTARGET//_/-} in
1044                 *-hardfloat-*|*eabihf) confgcc+=( --with-float=hard ) ;;
1045                 esac
1046         esac
1047
1048         local with_abi_map=()
1049         case $(tc-arch) in
1050         arm)    #264534 #414395
1051                 local a arm_arch=${CTARGET%%-*}
1052                 # Remove trailing endian variations first: eb el be bl b l
1053                 for a in e{b,l} {b,l}e b l ; do
1054                         if [[ ${arm_arch} == *${a} ]] ; then
1055                                 arm_arch=${arm_arch%${a}}
1056                                 break
1057                         fi
1058                 done
1059                 # Convert armv7{a,r,m} to armv7-{a,r,m}
1060                 [[ ${arm_arch} == armv7? ]] && arm_arch=${arm_arch/7/7-}
1061                 # See if this is a valid --with-arch flag
1062                 if (srcdir=${S}/gcc target=${CTARGET} with_arch=${arm_arch};
1063                     . "${srcdir}"/config.gcc) &>/dev/null
1064                 then
1065                         confgcc+=( --with-arch=${arm_arch} )
1066                 fi
1067
1068                 # Make default mode thumb for microcontroller classes #418209
1069                 [[ ${arm_arch} == *-m ]] && confgcc+=( --with-mode=thumb )
1070
1071                 # Enable hardvfp
1072                 if [[ $(tc-is-softfloat) == "no" ]] && \
1073                    [[ ${CTARGET} == armv[67]* ]] && \
1074                    tc_version_is_at_least 4.5
1075                 then
1076                         # Follow the new arm hardfp distro standard by default
1077                         confgcc+=( --with-float=hard )
1078                         case ${CTARGET} in
1079                         armv6*) confgcc+=( --with-fpu=vfp ) ;;
1080                         armv7*) confgcc+=( --with-fpu=vfpv3-d16 ) ;;
1081                         esac
1082                 fi
1083                 ;;
1084         mips)
1085                 # Add --with-abi flags to set default ABI
1086                 confgcc+=( --with-abi=$(gcc-abi-map ${TARGET_DEFAULT_ABI}) )
1087                 ;;
1088         amd64)
1089                 # drop the older/ABI checks once this get's merged into some
1090                 # version of gcc upstream
1091                 if tc_version_is_at_least 4.8 && has x32 $(get_all_abis TARGET) ; then
1092                         confgcc+=( --with-abi=$(gcc-abi-map ${TARGET_DEFAULT_ABI}) )
1093                 fi
1094                 ;;
1095         x86)
1096                 # Default arch for x86 is normally i386, lets give it a bump
1097                 # since glibc will do so based on CTARGET anyways
1098                 confgcc+=( --with-arch=${CTARGET%%-*} )
1099                 ;;
1100         hppa)
1101                 # Enable sjlj exceptions for backward compatibility on hppa
1102                 [[ ${GCCMAJOR} == "3" ]] && confgcc+=( --enable-sjlj-exceptions )
1103                 ;;
1104         ppc)
1105                 # Set up defaults based on current CFLAGS
1106                 is-flagq -mfloat-gprs=double && confgcc+=( --enable-e500-double )
1107                 [[ ${CTARGET//_/-} == *-e500v2-* ]] && confgcc+=( --enable-e500-double )
1108                 ;;
1109         esac
1110
1111         # if the target can do biarch (-m32/-m64), enable it.  overhead should
1112         # be small, and should simplify building of 64bit kernels in a 32bit
1113         # userland by not needing sys-devel/kgcc64.  #349405
1114         case $(tc-arch) in
1115         ppc|ppc64) tc_version_is_at_least 3.4 && confgcc+=( --enable-targets=all ) ;;
1116         sparc)     tc_version_is_at_least 4.4 && confgcc+=( --enable-targets=all ) ;;
1117         amd64|x86) tc_version_is_at_least 4.3 && confgcc+=( --enable-targets=all ) ;;
1118         esac
1119
1120         # On Darwin we need libdir to be set in order to get correct install names
1121         # for things like libobjc-gnu, libgcj and libfortran.  If we enable it on
1122         # non-Darwin we screw up the behaviour this eclass relies on.  We in
1123         # particular need this over --libdir for bug #255315.
1124         [[ ${CTARGET} == *-darwin* ]] && \
1125                 confgcc+=( --enable-version-specific-runtime-libs )
1126
1127         ### library options
1128
1129         if ! is_gcj ; then
1130                 confgcc+=( --disable-libgcj )
1131         elif use awt ; then
1132                 confgcc+=( --enable-java-awt=gtk )
1133         fi
1134
1135         if tc_version_is_at_least 4.2 ; then
1136                 if in_iuse openmp ; then
1137                         # Make sure target has pthreads support. #326757 #335883
1138                         # There shouldn't be a chicken & egg problem here as openmp won't
1139                         # build without a C library, and you can't build that w/out
1140                         # already having a compiler ...
1141                         if ! is_crosscompile || \
1142                            $(tc-getCPP ${CTARGET}) -E - <<<"#include <pthread.h>" >& /dev/null
1143                         then
1144                                 confgcc+=( $(use_enable openmp libgomp) )
1145                         else
1146                                 # Force disable as the configure script can be dumb #359855
1147                                 confgcc+=( --disable-libgomp )
1148                         fi
1149                 else
1150                         # For gcc variants where we don't want openmp (e.g. kgcc)
1151                         confgcc+=( --disable-libgomp )
1152                 fi
1153         fi
1154
1155         if tc_version_is_at_least 4.0 ; then
1156                 if in_iuse mudflap ; then
1157                         confgcc+=( $(use_enable mudflap libmudflap) )
1158                 else
1159                         confgcc+=( --disable-libmudflap )
1160                 fi
1161
1162                 if use_if_iuse libssp ; then
1163                         confgcc+=( --enable-libssp )
1164                 else
1165                         if hardened_gcc_is_stable ssp; then
1166                                 export gcc_cv_libc_provides_ssp=yes
1167                         fi
1168                         confgcc+=( --disable-libssp )
1169                 fi
1170         fi
1171
1172         if in_iuse cilk ; then
1173                 confgcc+=( $(use_enable cilk libcilkrts) )
1174         fi
1175
1176         # newer gcc's come with libquadmath, but only fortran uses
1177         # it, so auto punt it when we don't care
1178         if tc_version_is_at_least 4.6 && ! is_fortran ; then
1179                 confgcc+=( --disable-libquadmath )
1180         fi
1181
1182         if tc_version_is_at_least 4.6 ; then
1183                 confgcc+=( --enable-lto )
1184         elif tc_version_is_at_least 4.5 ; then
1185                 confgcc+=( --disable-lto )
1186         fi
1187
1188         # graphite was added in 4.4 but we only support it in 4.8+ due to external
1189         # library issues.  #448024
1190         if tc_version_is_at_least 5.0 ; then
1191                 confgcc+=( $(use_with graphite isl) )
1192                 use graphite && confgcc+=( --disable-isl-version-check )
1193         elif tc_version_is_at_least 4.8 ; then
1194                 confgcc+=( $(use_with graphite cloog) )
1195                 use graphite && confgcc+=( --disable-isl-version-check )
1196         elif tc_version_is_at_least 4.4 ; then
1197                 confgcc+=( --without-{cloog,ppl} )
1198         fi
1199
1200         if tc_version_is_at_least 4.8 ; then
1201                 confgcc+=( $(use_enable sanitize libsanitizer) )
1202         fi
1203
1204         if tc_version_is_at_least 6.0 ; then
1205                 confgcc+=(
1206                         $(use_enable pie default-pie)
1207                         # This defaults to -fstack-protector-strong.
1208                         $(use_enable ssp default-ssp)
1209                 )
1210         fi
1211
1212         # Disable gcc info regeneration -- it ships with generated info pages
1213         # already.  Our custom version/urls/etc... trigger it.  #464008
1214         export gcc_cv_prog_makeinfo_modern=no
1215
1216         # Do not let the X detection get in our way.  We know things can be found
1217         # via system paths, so no need to hardcode things that'll break multilib.
1218         # Older gcc versions will detect ac_x_libraries=/usr/lib64 which ends up
1219         # killing the 32bit builds which want /usr/lib.
1220         export ac_cv_have_x='have_x=yes ac_x_includes= ac_x_libraries='
1221
1222         confgcc+=( "$@" ${EXTRA_ECONF} )
1223
1224         # Nothing wrong with a good dose of verbosity
1225         echo
1226         einfo "PREFIX:          ${PREFIX}"
1227         einfo "BINPATH:         ${BINPATH}"
1228         einfo "LIBPATH:         ${LIBPATH}"
1229         einfo "DATAPATH:        ${DATAPATH}"
1230         einfo "STDCXX_INCDIR:   ${STDCXX_INCDIR}"
1231         echo
1232         einfo "Languages:       ${GCC_LANG}"
1233         echo
1234         einfo "Configuring GCC with: ${confgcc[@]//--/\n\t--}"
1235         echo
1236
1237         # Build in a separate build tree
1238         mkdir -p "${WORKDIR}"/build
1239         pushd "${WORKDIR}"/build > /dev/null
1240
1241         # and now to do the actual configuration
1242         addwrite /dev/zero
1243         echo "${S}"/configure "${confgcc[@]}"
1244         # Older gcc versions did not detect bash and re-exec itself, so force the
1245         # use of bash.  Newer ones will auto-detect, but this is not harmeful.
1246         CONFIG_SHELL="/bin/bash" \
1247         bash "${S}"/configure "${confgcc[@]}" || die "failed to run configure"
1248
1249         # return to whatever directory we were in before
1250         popd > /dev/null
1251 }
1252
1253 # Replace -m flags unsupported by the version being built with the best
1254 # available equivalent
1255 downgrade_arch_flags() {
1256         local arch bver i isa myarch mytune rep ver
1257
1258         bver=${1:-${GCC_BRANCH_VER}}
1259         [[ $(gcc-version) < ${bver} ]] && return 0
1260         [[ $(tc-arch) != amd64 && $(tc-arch) != x86 ]] && return 0
1261
1262         myarch=$(get-flag march)
1263         mytune=$(get-flag mtune)
1264
1265         # If -march=native isn't supported we have to tease out the actual arch
1266         if [[ ${myarch} == native || ${mytune} == native ]] ; then
1267                 if [[ ${bver} < 4.2 ]] ; then
1268                         arch=$($(tc-getCC) -march=native -v -E -P - </dev/null 2>&1 \
1269                                 | sed -rn "/cc1.*-march/s:.*-march=([^ ']*).*:\1:p")
1270                         replace-cpu-flags native ${arch}
1271                 fi
1272         fi
1273
1274         # Handle special -mtune flags
1275         [[ ${mytune} == intel && ${bver} < 4.9 ]] && replace-cpu-flags intel generic
1276         [[ ${mytune} == generic && ${bver} < 4.2 ]] && filter-flags '-mtune=*'
1277         [[ ${mytune} == x86-64 ]] && filter-flags '-mtune=*'
1278         [[ ${bver} < 3.4 ]] && filter-flags '-mtune=*'
1279
1280         # "added" "arch" "replacement"
1281         local archlist=(
1282                 4.9 bdver4 bdver3
1283                 4.9 bonnell atom
1284                 4.9 broadwell core-avx2
1285                 4.9 haswell core-avx2
1286                 4.9 ivybridge core-avx-i
1287                 4.9 nehalem corei7
1288                 4.9 sandybridge corei7-avx
1289                 4.9 silvermont corei7
1290                 4.9 westmere corei7
1291                 4.8 bdver3 bdver2
1292                 4.8 btver2 btver1
1293                 4.7 bdver2 bdver1
1294                 4.7 core-avx2 core-avx-i
1295                 4.6 bdver1 amdfam10
1296                 4.6 btver1 amdfam10
1297                 4.6 core-avx-i core2
1298                 4.6 corei7 core2
1299                 4.6 corei7-avx core2
1300                 4.5 atom core2
1301                 4.3 amdfam10 k8
1302                 4.3 athlon64-sse3 k8
1303                 4.3 barcelona k8
1304                 4.3 core2 nocona
1305                 4.3 geode k6-2 # gcc.gnu.org/PR41989#c22
1306                 4.3 k8-sse3 k8
1307                 4.3 opteron-sse3 k8
1308                 3.4 athlon-fx x86-64
1309                 3.4 athlon64 x86-64
1310                 3.4 c3-2 c3
1311                 3.4 k8 x86-64
1312                 3.4 opteron x86-64
1313                 3.4 pentium-m pentium3
1314                 3.4 pentium3m pentium3
1315                 3.4 pentium4m pentium4
1316         )
1317
1318         for ((i = 0; i < ${#archlist[@]}; i += 3)) ; do
1319                 myarch=$(get-flag march)
1320                 mytune=$(get-flag mtune)
1321
1322                 ver=${archlist[i]}
1323                 arch=${archlist[i + 1]}
1324                 rep=${archlist[i + 2]}
1325
1326                 [[ ${myarch} != ${arch} && ${mytune} != ${arch} ]] && continue
1327
1328                 if [[ ${ver} > ${bver} ]] ; then
1329                         einfo "Replacing ${myarch} (added in gcc ${ver}) with ${rep}..."
1330                         [[ ${myarch} == ${arch} ]] && replace-cpu-flags ${myarch} ${rep}
1331                         [[ ${mytune} == ${arch} ]] && replace-cpu-flags ${mytune} ${rep}
1332                         continue
1333                 else
1334                         break
1335                 fi
1336         done
1337
1338         # we only check -mno* here since -m* get removed by strip-flags later on
1339         local isalist=(
1340                 4.9 -mno-sha
1341                 4.9 -mno-avx512pf
1342                 4.9 -mno-avx512f
1343                 4.9 -mno-avx512er
1344                 4.9 -mno-avx512cd
1345                 4.8 -mno-xsaveopt
1346                 4.8 -mno-xsave
1347                 4.8 -mno-rtm
1348                 4.8 -mno-fxsr
1349                 4.7 -mno-lzcnt
1350                 4.7 -mno-bmi2
1351                 4.7 -mno-avx2
1352                 4.6 -mno-tbm
1353                 4.6 -mno-rdrnd
1354                 4.6 -mno-fsgsbase
1355                 4.6 -mno-f16c
1356                 4.6 -mno-bmi
1357                 4.5 -mno-xop
1358                 4.5 -mno-movbe
1359                 4.5 -mno-lwp
1360                 4.5 -mno-fma4
1361                 4.4 -mno-pclmul
1362                 4.4 -mno-fma
1363                 4.4 -mno-avx
1364                 4.4 -mno-aes
1365                 4.3 -mno-ssse3
1366                 4.3 -mno-sse4a
1367                 4.3 -mno-sse4
1368                 4.3 -mno-sse4.2
1369                 4.3 -mno-sse4.1
1370                 4.3 -mno-popcnt
1371                 4.3 -mno-abm
1372         )
1373
1374         for ((i = 0; i < ${#isalist[@]}; i += 2)) ; do
1375                 ver=${isalist[i]}
1376                 isa=${isalist[i + 1]}
1377                 [[ ${ver} > ${bver} ]] && filter-flags ${isa} ${isa/-m/-mno-}
1378         done
1379 }
1380
1381 gcc_do_filter_flags() {
1382         strip-flags
1383         replace-flags -O? -O2
1384
1385         # dont want to funk ourselves
1386         filter-flags '-mabi*' -m31 -m32 -m64
1387
1388         filter-flags -frecord-gcc-switches # 490738
1389         filter-flags -mno-rtm -mno-htm # 506202
1390
1391         if tc_version_is_between 3.2 3.4 ; then
1392                 # XXX: this is so outdated it's barely useful, but it don't hurt...
1393                 replace-cpu-flags G3 750
1394                 replace-cpu-flags G4 7400
1395                 replace-cpu-flags G5 7400
1396
1397                 # XXX: should add a sed or something to query all supported flags
1398                 #      from the gcc source and trim everything else ...
1399                 filter-flags -f{no-,}unit-at-a-time -f{no-,}web -mno-tls-direct-seg-refs
1400                 filter-flags -f{no-,}stack-protector{,-all}
1401                 filter-flags -fvisibility-inlines-hidden -fvisibility=hidden
1402         fi
1403
1404         if tc_version_is_at_least 3.4 ; then
1405                 case $(tc-arch) in
1406                         amd64|x86)
1407                                 filter-flags '-mcpu=*'
1408
1409                                 tc_version_is_between 4.4 4.5 && append-flags -mno-avx # 357287
1410
1411                                 if tc_version_is_between 4.6 4.7 ; then
1412                                         # https://bugs.gentoo.org/411333
1413                                         # https://bugs.gentoo.org/466454
1414                                         replace-cpu-flags c3-2 pentium2 pentium3 pentium3m pentium-m i686
1415                                 fi
1416                                 ;;
1417                         alpha)
1418                                 # https://bugs.gentoo.org/454426
1419                                 append-ldflags -Wl,--no-relax
1420                                 ;;
1421                         sparc)
1422                                 # temporary workaround for random ICEs reproduced by multiple users
1423                                 # https://bugs.gentoo.org/457062
1424                                 tc_version_is_between 4.6 4.8 && MAKEOPTS+=" -j1"
1425                                 ;;
1426                         *-macos)
1427                                 # http://gcc.gnu.org/PR25127
1428                                 tc_version_is_between 4.0 4.2 && \
1429                                         filter-flags '-mcpu=*' '-march=*' '-mtune=*'
1430                                 ;;
1431                 esac
1432         fi
1433
1434         strip-unsupported-flags
1435
1436         # these are set here so we have something sane at configure time
1437         if is_crosscompile ; then
1438                 # Set this to something sane for both native and target
1439                 CFLAGS="-O2 -pipe"
1440                 FFLAGS=${CFLAGS}
1441                 FCFLAGS=${CFLAGS}
1442
1443                 local VAR="CFLAGS_"${CTARGET//-/_}
1444                 CXXFLAGS=${!VAR}
1445         fi
1446
1447         export GCJFLAGS=${GCJFLAGS:-${CFLAGS}}
1448 }
1449
1450 setup_minispecs_gcc_build_specs() {
1451         # Setup the "build.specs" file for gcc 4.3 to use when building.
1452         if hardened_gcc_works pie ; then
1453                 cat "${WORKDIR}"/specs/pie.specs >> "${WORKDIR}"/build.specs
1454         fi
1455         if hardened_gcc_works ssp ; then
1456                 for s in ssp sspall ; do
1457                         cat "${WORKDIR}"/specs/${s}.specs >> "${WORKDIR}"/build.specs
1458                 done
1459         fi
1460         for s in nostrict znow ; do
1461                 cat "${WORKDIR}"/specs/${s}.specs >> "${WORKDIR}"/build.specs
1462         done
1463         export GCC_SPECS="${WORKDIR}"/build.specs
1464 }
1465
1466 gcc-multilib-configure() {
1467         if ! is_multilib ; then
1468                 confgcc+=( --disable-multilib )
1469                 # Fun times: if we are building for a target that has multiple
1470                 # possible ABI formats, and the user has told us to pick one
1471                 # that isn't the default, then not specifying it via the list
1472                 # below will break that on us.
1473         else
1474                 confgcc+=( --enable-multilib )
1475         fi
1476
1477         # translate our notion of multilibs into gcc's
1478         local abi list
1479         for abi in $(get_all_abis TARGET) ; do
1480                 local l=$(gcc-abi-map ${abi})
1481                 [[ -n ${l} ]] && list+=",${l}"
1482         done
1483         if [[ -n ${list} ]] ; then
1484                 case ${CTARGET} in
1485                 x86_64*)
1486                         tc_version_is_at_least 4.8 && confgcc+=( --with-multilib-list=${list:1} )
1487                         ;;
1488                 esac
1489         fi
1490 }
1491
1492 gcc-abi-map() {
1493         # Convert the ABI name we use in Gentoo to what gcc uses
1494         local map=()
1495         case ${CTARGET} in
1496         mips*)   map=("o32 32" "n32 n32" "n64 64") ;;
1497         x86_64*) map=("amd64 m64" "x86 m32" "x32 mx32") ;;
1498         esac
1499
1500         local m
1501         for m in "${map[@]}" ; do
1502                 l=( ${m} )
1503                 [[ $1 == ${l[0]} ]] && echo ${l[1]} && break
1504         done
1505 }
1506
1507 #----> src_compile <----
1508
1509 toolchain_src_compile() {
1510         touch "${S}"/gcc/c-gperf.h
1511
1512         # Do not make manpages if we do not have perl ...
1513         [[ ! -x /usr/bin/perl ]] \
1514                 && find "${WORKDIR}"/build -name '*.[17]' -exec touch {} +
1515
1516         gcc_do_make ${GCC_MAKE_TARGET}
1517 }
1518
1519 gcc_do_make() {
1520         # This function accepts one optional argument, the make target to be used.
1521         # If omitted, gcc_do_make will try to guess whether it should use all,
1522         # or bootstrap-lean depending on CTARGET and arch.
1523         # An example of how to use this function:
1524         #
1525         #       gcc_do_make all-target-libstdc++-v3
1526
1527         [[ -n ${1} ]] && GCC_MAKE_TARGET=${1}
1528
1529         # default target
1530         if is_crosscompile || tc-is-cross-compiler ; then
1531                 # 3 stage bootstrapping doesnt quite work when you cant run the
1532                 # resulting binaries natively ^^;
1533                 GCC_MAKE_TARGET=${GCC_MAKE_TARGET-all}
1534         else
1535                 GCC_MAKE_TARGET=${GCC_MAKE_TARGET-bootstrap-lean}
1536         fi
1537
1538         # Older versions of GCC could not do profiledbootstrap in parallel due to
1539         # collisions with profiling info.
1540         # boundschecking also seems to introduce parallel build issues.
1541         if [[ ${GCC_MAKE_TARGET} == "profiledbootstrap" ]] || use_if_iuse boundschecking ; then
1542                 ! tc_version_is_at_least 4.6 && export MAKEOPTS="${MAKEOPTS} -j1"
1543         fi
1544
1545         if [[ ${GCC_MAKE_TARGET} == "all" ]] ; then
1546                 STAGE1_CFLAGS=${STAGE1_CFLAGS-"${CFLAGS}"}
1547         elif [[ $(gcc-version) == "3.4" && ${GCC_BRANCH_VER} == "3.4" ]] && gcc-specs-ssp ; then
1548                 # See bug #79852
1549                 STAGE1_CFLAGS=${STAGE1_CFLAGS-"-O2"}
1550         fi
1551
1552         if is_crosscompile; then
1553                 # In 3.4, BOOT_CFLAGS is never used on a crosscompile...
1554                 # but I'll leave this in anyways as someone might have had
1555                 # some reason for putting it in here... --eradicator
1556                 BOOT_CFLAGS=${BOOT_CFLAGS-"-O2"}
1557         else
1558                 # we only want to use the system's CFLAGS if not building a
1559                 # cross-compiler.
1560                 BOOT_CFLAGS=${BOOT_CFLAGS-"$(get_abi_CFLAGS ${TARGET_DEFAULT_ABI}) ${CFLAGS}"}
1561         fi
1562
1563         einfo "Compiling ${PN} (${GCC_MAKE_TARGET})..."
1564
1565         pushd "${WORKDIR}"/build >/dev/null
1566
1567         emake \
1568                 LDFLAGS="${LDFLAGS}" \
1569                 STAGE1_CFLAGS="${STAGE1_CFLAGS}" \
1570                 LIBPATH="${LIBPATH}" \
1571                 BOOT_CFLAGS="${BOOT_CFLAGS}" \
1572                 ${GCC_MAKE_TARGET} \
1573                 || die "emake failed with ${GCC_MAKE_TARGET}"
1574
1575         if ! is_crosscompile && use cxx && use_if_iuse doc ; then
1576                 if type -p doxygen > /dev/null ; then
1577                         if tc_version_is_at_least 4.3 ; then
1578                                 cd "${CTARGET}"/libstdc++-v3/doc
1579                                 emake doc-man-doxygen || ewarn "failed to make docs"
1580                         elif tc_version_is_at_least 3.0 ; then
1581                                 cd "${CTARGET}"/libstdc++-v3
1582                                 emake doxygen-man || ewarn "failed to make docs"
1583                         fi
1584                         # Clean bogus manpages.  #113902
1585                         find -name '*_build_*' -delete
1586                         # Blow away generated directory references.  Newer versions of gcc
1587                         # have gotten better at this, but not perfect.  This is easier than
1588                         # backporting all of the various doxygen patches.  #486754
1589                         find -name '*_.3' -exec grep -l ' Directory Reference ' {} + | \
1590                                 xargs rm -f
1591                 else
1592                         ewarn "Skipping libstdc++ manpage generation since you don't have doxygen installed"
1593                 fi
1594         fi
1595
1596         popd >/dev/null
1597 }
1598
1599 #---->> src_test <<----
1600
1601 toolchain_src_test() {
1602         if use regression-test ; then
1603                 cd "${WORKDIR}"/build
1604                 emake -k check
1605         fi
1606 }
1607
1608 #---->> src_install <<----
1609
1610 toolchain_src_install() {
1611         cd "${WORKDIR}"/build
1612
1613         # Do allow symlinks in private gcc include dir as this can break the build
1614         find gcc/include*/ -type l -delete
1615
1616         # Copy over the info pages.  We disabled their generation earlier, but the
1617         # build system only expects to install out of the build dir, not the source.  #464008
1618         mkdir -p gcc/doc
1619         local x=
1620         for x in "${S}"/gcc/doc/*.info* ; do
1621                 if [[ -f ${x} ]] ; then
1622                         cp "${x}" gcc/doc/ || die
1623                 fi
1624         done
1625
1626         # We remove the generated fixincludes, as they can cause things to break
1627         # (ncurses, openssl, etc).  We do not prevent them from being built, as
1628         # in the following commit which we revert:
1629         # https://sources.gentoo.org/cgi-bin/viewvc.cgi/gentoo-x86/eclass/toolchain.eclass?r1=1.647&r2=1.648
1630         # This is because bsd userland needs fixedincludes to build gcc, while
1631         # linux does not.  Both can dispose of them afterwards.
1632         while read x ; do
1633                 grep -q 'It has been auto-edited by fixincludes from' "${x}" \
1634                         && rm -f "${x}"
1635         done < <(find gcc/include*/ -name '*.h')
1636
1637         # Do the 'make install' from the build directory
1638         S="${WORKDIR}"/build emake -j1 DESTDIR="${D}" install || die
1639
1640         # Punt some tools which are really only useful while building gcc
1641         find "${D}" -name install-tools -prune -type d -exec rm -rf "{}" \;
1642         # This one comes with binutils
1643         find "${D}" -name libiberty.a -delete
1644
1645         # Move the libraries to the proper location
1646         gcc_movelibs
1647
1648         # Basic sanity check
1649         if ! is_crosscompile ; then
1650                 local EXEEXT
1651                 eval $(grep ^EXEEXT= "${WORKDIR}"/build/gcc/config.log)
1652                 [[ -r ${D}${BINPATH}/gcc${EXEEXT} ]] || die "gcc not found in ${D}"
1653         fi
1654
1655         dodir /etc/env.d/gcc
1656         create_gcc_env_entry
1657
1658         # Setup the gcc_env_entry for hardened gcc 4 with minispecs
1659         want_minispecs && copy_minispecs_gcc_specs
1660
1661         # Make sure we dont have stuff lying around that
1662         # can nuke multiple versions of gcc
1663         gcc_slot_java
1664
1665         dodir /usr/bin
1666         cd "${D}"${BINPATH}
1667         # Ugh: we really need to auto-detect this list.
1668         #      It's constantly out of date.
1669         for x in cpp gcc g++ c++ gcov g77 gcj gcjh gfortran gccgo ; do
1670                 # For some reason, g77 gets made instead of ${CTARGET}-g77...
1671                 # this should take care of that
1672                 if [[ -f ${x} ]] ; then
1673                         # In case they're hardlinks, clear out the target first
1674                         # otherwise the mv below will complain.
1675                         rm -f ${CTARGET}-${x}
1676                         mv ${x} ${CTARGET}-${x}
1677                 fi
1678
1679                 if [[ -f ${CTARGET}-${x} ]] ; then
1680                         if ! is_crosscompile ; then
1681                                 ln -sf ${CTARGET}-${x} ${x}
1682                                 dosym ${BINPATH}/${CTARGET}-${x} \
1683                                         /usr/bin/${x}-${GCC_CONFIG_VER}
1684                         fi
1685                         # Create versioned symlinks
1686                         dosym ${BINPATH}/${CTARGET}-${x} \
1687                                 /usr/bin/${CTARGET}-${x}-${GCC_CONFIG_VER}
1688                 fi
1689
1690                 if [[ -f ${CTARGET}-${x}-${GCC_CONFIG_VER} ]] ; then
1691                         rm -f ${CTARGET}-${x}-${GCC_CONFIG_VER}
1692                         ln -sf ${CTARGET}-${x} ${CTARGET}-${x}-${GCC_CONFIG_VER}
1693                 fi
1694         done
1695         # Clear out the main go binaries as we don't want to clobber dev-lang/go
1696         # when gcc-config runs. #567806
1697         if tc_version_is_at_least 5 && is_go ; then
1698                 rm -f go gofmt
1699         fi
1700
1701         # Now do the fun stripping stuff
1702         env RESTRICT="" CHOST=${CHOST} prepstrip "${D}${BINPATH}"
1703         is_crosscompile && \
1704                 env RESTRICT="" CHOST=${CHOST} prepstrip "${D}/${HOSTLIBPATH}"
1705         env RESTRICT="" CHOST=${CTARGET} prepstrip "${D}${LIBPATH}"
1706         # gcc used to install helper binaries in lib/ but then moved to libexec/
1707         [[ -d ${D}${PREFIX}/libexec/gcc ]] && \
1708                 env RESTRICT="" CHOST=${CHOST} prepstrip "${D}${PREFIX}/libexec/gcc/${CTARGET}/${GCC_CONFIG_VER}"
1709
1710         cd "${S}"
1711         if is_crosscompile; then
1712                 rm -rf "${D}"/usr/share/{man,info}
1713                 rm -rf "${D}"${DATAPATH}/{man,info}
1714         else
1715                 if tc_version_is_at_least 3.0 ; then
1716                         local cxx_mandir=$(find "${WORKDIR}/build/${CTARGET}/libstdc++-v3" -name man)
1717                         if [[ -d ${cxx_mandir} ]] ; then
1718                                 cp -r "${cxx_mandir}"/man? "${D}/${DATAPATH}"/man/
1719                         fi
1720                 fi
1721                 has noinfo ${FEATURES} \
1722                         && rm -r "${D}/${DATAPATH}"/info \
1723                         || prepinfo "${DATAPATH}"
1724                 has noman ${FEATURES} \
1725                         && rm -r "${D}/${DATAPATH}"/man \
1726                         || prepman "${DATAPATH}"
1727         fi
1728         # prune empty dirs left behind
1729         find "${D}" -depth -type d -delete 2>/dev/null
1730
1731         # install testsuite results
1732         if use regression-test; then
1733                 docinto testsuite
1734                 find "${WORKDIR}"/build -type f -name "*.sum" -exec dodoc {} +
1735                 find "${WORKDIR}"/build -type f -path "*/testsuite/*.log" -exec dodoc {} +
1736         fi
1737
1738         # Rather install the script, else portage with changing $FILESDIR
1739         # between binary and source package borks things ....
1740         if ! is_crosscompile ; then
1741                 insinto "${DATAPATH}"
1742                 newins "${GCC_FILESDIR}"/awk/fixlafiles.awk-no_gcc_la fixlafiles.awk || die
1743                 find "${D}/${LIBPATH}" -name libstdc++.la -type f -delete
1744                 find "${D}/${LIBPATH}" -name 'lib*san.la' -type f -delete #487550 #546700
1745                 exeinto "${DATAPATH}"
1746                 doexe "${GCC_FILESDIR}"/fix_libtool_files.sh || die
1747                 doexe "${GCC_FILESDIR}"/c{89,99} || die
1748         fi
1749
1750         # Use gid of 0 because some stupid ports don't have
1751         # the group 'root' set to gid 0.  Send to /dev/null
1752         # for people who are testing as non-root.
1753         chown -R root:0 "${D}"${LIBPATH} 2>/dev/null
1754
1755         # Move pretty-printers to gdb datadir to shut ldconfig up
1756         local py gdbdir=/usr/share/gdb/auto-load${LIBPATH/\/lib\//\/$(get_libdir)\/}
1757         pushd "${D}"${LIBPATH} >/dev/null
1758         for py in $(find . -name '*-gdb.py') ; do
1759                 local multidir=${py%/*}
1760                 insinto "${gdbdir}/${multidir}"
1761                 sed -i "/^libdir =/s:=.*:= '${LIBPATH}/${multidir}':" "${py}" || die #348128
1762                 doins "${py}" || die
1763                 rm "${py}" || die
1764         done
1765         popd >/dev/null
1766
1767         # Don't scan .gox files for executable stacks - false positives
1768         export QA_EXECSTACK="usr/lib*/go/*/*.gox"
1769         export QA_WX_LOAD="usr/lib*/go/*/*.gox"
1770
1771         # Disable RANDMMAP so PCH works. #301299
1772         if tc_version_is_at_least 4.3 ; then
1773                 pax-mark -r "${D}${PREFIX}/libexec/gcc/${CTARGET}/${GCC_CONFIG_VER}/cc1"
1774                 pax-mark -r "${D}${PREFIX}/libexec/gcc/${CTARGET}/${GCC_CONFIG_VER}/cc1plus"
1775         fi
1776 }
1777
1778 # Move around the libs to the right location.  For some reason,
1779 # when installing gcc, it dumps internal libraries into /usr/lib
1780 # instead of the private gcc lib path
1781 gcc_movelibs() {
1782         # older versions of gcc did not support --print-multi-os-directory
1783         tc_version_is_at_least 3.2 || return 0
1784
1785         # For non-target libs which are for CHOST and not CTARGET, we want to
1786         # move them to the compiler-specific CHOST internal dir.  This is stuff
1787         # that you want to link against when building tools rather than building
1788         # code to run on the target.
1789         if tc_version_is_at_least 5 && is_crosscompile ; then
1790                 dodir "${HOSTLIBPATH}"
1791                 mv "${D}"/usr/$(get_libdir)/libcc1* "${D}${HOSTLIBPATH}" || die
1792         fi
1793
1794         # For all the libs that are built for CTARGET, move them into the
1795         # compiler-specific CTARGET internal dir.
1796         local x multiarg removedirs=""
1797         for multiarg in $($(XGCC) -print-multi-lib) ; do
1798                 multiarg=${multiarg#*;}
1799                 multiarg=${multiarg//@/ -}
1800
1801                 local OS_MULTIDIR=$($(XGCC) ${multiarg} --print-multi-os-directory)
1802                 local MULTIDIR=$($(XGCC) ${multiarg} --print-multi-directory)
1803                 local TODIR=${D}${LIBPATH}/${MULTIDIR}
1804                 local FROMDIR=
1805
1806                 [[ -d ${TODIR} ]] || mkdir -p ${TODIR}
1807
1808                 for FROMDIR in \
1809                         ${LIBPATH}/${OS_MULTIDIR} \
1810                         ${LIBPATH}/../${MULTIDIR} \
1811                         ${PREFIX}/lib/${OS_MULTIDIR} \
1812                         ${PREFIX}/${CTARGET}/lib/${OS_MULTIDIR}
1813                 do
1814                         removedirs="${removedirs} ${FROMDIR}"
1815                         FROMDIR=${D}${FROMDIR}
1816                         if [[ ${FROMDIR} != "${TODIR}" && -d ${FROMDIR} ]] ; then
1817                                 local files=$(find "${FROMDIR}" -maxdepth 1 ! -type d 2>/dev/null)
1818                                 if [[ -n ${files} ]] ; then
1819                                         mv ${files} "${TODIR}" || die
1820                                 fi
1821                         fi
1822                 done
1823                 fix_libtool_libdir_paths "${LIBPATH}/${MULTIDIR}"
1824
1825                 # SLOT up libgcj.pc if it's available (and let gcc-config worry about links)
1826                 FROMDIR="${PREFIX}/lib/${OS_MULTIDIR}"
1827                 for x in "${D}${FROMDIR}"/pkgconfig/libgcj*.pc ; do
1828                         [[ -f ${x} ]] || continue
1829                         sed -i "/^libdir=/s:=.*:=${LIBPATH}/${MULTIDIR}:" "${x}" || die
1830                         mv "${x}" "${D}${FROMDIR}"/pkgconfig/libgcj-${GCC_PV}.pc || die
1831                 done
1832         done
1833
1834         # We remove directories separately to avoid this case:
1835         #       mv SRC/lib/../lib/*.o DEST
1836         #       rmdir SRC/lib/../lib/
1837         #       mv SRC/lib/../lib32/*.o DEST  # Bork
1838         for FROMDIR in ${removedirs} ; do
1839                 rmdir "${D}"${FROMDIR} >& /dev/null
1840         done
1841         find -depth "${D}" -type d -exec rmdir {} + >& /dev/null
1842 }
1843
1844 # make sure the libtool archives have libdir set to where they actually
1845 # -are-, and not where they -used- to be.  also, any dependencies we have
1846 # on our own .la files need to be updated.
1847 fix_libtool_libdir_paths() {
1848         local libpath="$1"
1849
1850         pushd "${D}" >/dev/null
1851
1852         pushd "./${libpath}" >/dev/null
1853         local dir="${PWD#${D%/}}"
1854         local allarchives=$(echo *.la)
1855         allarchives="\(${allarchives// /\\|}\)"
1856         popd >/dev/null
1857
1858         # The libdir might not have any .la files. #548782
1859         find "./${dir}" -maxdepth 1 -name '*.la' \
1860                 -exec sed -i -e "/^libdir=/s:=.*:='${dir}':" {} + || die
1861         # Would be nice to combine these, but -maxdepth can not be specified
1862         # on sub-expressions.
1863         find "./${PREFIX}"/lib* -maxdepth 3 -name '*.la' \
1864                 -exec sed -i -e "/^dependency_libs=/s:/[^ ]*/${allarchives}:${libpath}/\1:g" {} + || die
1865         find "./${dir}/" -maxdepth 1 -name '*.la' \
1866                 -exec sed -i -e "/^dependency_libs=/s:/[^ ]*/${allarchives}:${libpath}/\1:g" {} + || die
1867
1868         popd >/dev/null
1869 }
1870
1871 create_gcc_env_entry() {
1872         dodir /etc/env.d/gcc
1873         local gcc_envd_base="/etc/env.d/gcc/${CTARGET}-${GCC_CONFIG_VER}"
1874
1875         local gcc_specs_file
1876         local gcc_envd_file="${D}${gcc_envd_base}"
1877         if [[ -z $1 ]] ; then
1878                 # I'm leaving the following commented out to remind me that it
1879                 # was an insanely -bad- idea. Stuff broke. GCC_SPECS isnt unset
1880                 # on chroot or in non-toolchain.eclass gcc ebuilds!
1881                 #gcc_specs_file="${LIBPATH}/specs"
1882                 gcc_specs_file=""
1883         else
1884                 gcc_envd_file+="-$1"
1885                 gcc_specs_file="${LIBPATH}/$1.specs"
1886         fi
1887
1888         # We want to list the default ABI's LIBPATH first so libtool
1889         # searches that directory first.  This is a temporary
1890         # workaround for libtool being stupid and using .la's from
1891         # conflicting ABIs by using the first one in the search path
1892         local ldpaths mosdirs
1893         if tc_version_is_at_least 3.2 ; then
1894                 local mdir mosdir abi ldpath
1895                 for abi in $(get_all_abis TARGET) ; do
1896                         mdir=$($(XGCC) $(get_abi_CFLAGS ${abi}) --print-multi-directory)
1897                         ldpath=${LIBPATH}
1898                         [[ ${mdir} != "." ]] && ldpath+="/${mdir}"
1899                         ldpaths="${ldpath}${ldpaths:+:${ldpaths}}"
1900
1901                         mosdir=$($(XGCC) $(get_abi_CFLAGS ${abi}) -print-multi-os-directory)
1902                         mosdirs="${mosdir}${mosdirs:+:${mosdirs}}"
1903                 done
1904         else
1905                 # Older gcc's didn't do multilib, so logic is simple.
1906                 ldpaths=${LIBPATH}
1907         fi
1908
1909         cat <<-EOF > ${gcc_envd_file}
1910         PATH="${BINPATH}"
1911         ROOTPATH="${BINPATH}"
1912         GCC_PATH="${BINPATH}"
1913         LDPATH="${ldpaths}"
1914         MANPATH="${DATAPATH}/man"
1915         INFOPATH="${DATAPATH}/info"
1916         STDCXX_INCDIR="${STDCXX_INCDIR##*/}"
1917         CTARGET="${CTARGET}"
1918         GCC_SPECS="${gcc_specs_file}"
1919         MULTIOSDIRS="${mosdirs}"
1920         EOF
1921 }
1922
1923 copy_minispecs_gcc_specs() {
1924         # setup the hardenedno* specs files and the vanilla specs file.
1925         if hardened_gcc_works ; then
1926                 create_gcc_env_entry hardenednopiessp
1927         fi
1928         if hardened_gcc_works pie ; then
1929                 create_gcc_env_entry hardenednopie
1930         fi
1931         if hardened_gcc_works ssp ; then
1932                 create_gcc_env_entry hardenednossp
1933         fi
1934         create_gcc_env_entry vanilla
1935         insinto ${LIBPATH}
1936         doins "${WORKDIR}"/specs/*.specs || die "failed to install specs"
1937         # Build system specs file which, if it exists, must be a complete set of
1938         # specs as it completely and unconditionally overrides the builtin specs.
1939         if ! tc_version_is_at_least 4.4 ; then
1940                 $(XGCC) -dumpspecs > "${WORKDIR}"/specs/specs
1941                 cat "${WORKDIR}"/build.specs >> "${WORKDIR}"/specs/specs
1942                 doins "${WORKDIR}"/specs/specs || die "failed to install the specs file"
1943         fi
1944 }
1945
1946 gcc_slot_java() {
1947         local x
1948
1949         # Move Java headers to compiler-specific dir
1950         for x in "${D}"${PREFIX}/include/gc*.h "${D}"${PREFIX}/include/j*.h ; do
1951                 [[ -f ${x} ]] && mv -f "${x}" "${D}"${LIBPATH}/include/
1952         done
1953         for x in gcj gnu java javax org ; do
1954                 if [[ -d ${D}${PREFIX}/include/${x} ]] ; then
1955                         dodir /${LIBPATH}/include/${x}
1956                         mv -f "${D}"${PREFIX}/include/${x}/* "${D}"${LIBPATH}/include/${x}/
1957                         rm -rf "${D}"${PREFIX}/include/${x}
1958                 fi
1959         done
1960
1961         if [[ -d ${D}${PREFIX}/lib/security ]] || [[ -d ${D}${PREFIX}/$(get_libdir)/security ]] ; then
1962                 dodir /${LIBPATH}/security
1963                 mv -f "${D}"${PREFIX}/lib*/security/* "${D}"${LIBPATH}/security
1964                 rm -rf "${D}"${PREFIX}/lib*/security
1965         fi
1966
1967         # Move random gcj files to compiler-specific directories
1968         for x in libgcj.spec logging.properties ; do
1969                 x="${D}${PREFIX}/lib/${x}"
1970                 [[ -f ${x} ]] && mv -f "${x}" "${D}"${LIBPATH}/
1971         done
1972
1973         # Rename jar because it could clash with Kaffe's jar if this gcc is
1974         # primary compiler (aka don't have the -<version> extension)
1975         cd "${D}"${BINPATH}
1976         [[ -f jar ]] && mv -f jar gcj-jar
1977 }
1978
1979 #---->> pkg_post* <<----
1980
1981 toolchain_pkg_postinst() {
1982         do_gcc_config
1983
1984         if ! is_crosscompile ; then
1985                 echo
1986                 ewarn "If you have issues with packages unable to locate libstdc++.la,"
1987                 ewarn "then try running 'fix_libtool_files.sh' on the old gcc versions."
1988                 echo
1989                 ewarn "You might want to review the GCC upgrade guide when moving between"
1990                 ewarn "major versions (like 4.2 to 4.3):"
1991                 ewarn "https://wiki.gentoo.org/wiki/Upgrading_GCC"
1992                 echo
1993
1994                 # Clean up old paths
1995                 rm -f "${ROOT}"/*/rcscripts/awk/fixlafiles.awk "${ROOT}"/sbin/fix_libtool_files.sh
1996                 rmdir "${ROOT}"/*/rcscripts{/awk,} 2>/dev/null
1997
1998                 mkdir -p "${ROOT}"/usr/{share/gcc-data,sbin,bin}
1999                 cp "${ROOT}/${DATAPATH}"/fixlafiles.awk "${ROOT}"/usr/share/gcc-data/ || die
2000                 cp "${ROOT}/${DATAPATH}"/fix_libtool_files.sh "${ROOT}"/usr/sbin/ || die
2001
2002                 # Since these aren't critical files and portage sucks with
2003                 # handling of binpkgs, don't require these to be found
2004                 cp "${ROOT}/${DATAPATH}"/c{89,99} "${ROOT}"/usr/bin/ 2>/dev/null
2005         fi
2006
2007         if use regression-test ; then
2008                 elog "Testsuite results have been installed into /usr/share/doc/${PF}/testsuite"
2009                 echo
2010         fi
2011
2012         if [[ -n ${PRERELEASE}${SNAPSHOT} ]] ; then
2013                 einfo "This GCC ebuild is provided for your convenience, and the use"
2014                 einfo "of this compiler is not supported by the Gentoo Developers."
2015                 einfo "Please report bugs to upstream at http://gcc.gnu.org/bugzilla/"
2016         fi
2017 }
2018
2019 toolchain_pkg_postrm() {
2020         # to make our lives easier (and saner), we do the fix_libtool stuff here.
2021         # rather than checking SLOT's and trying in upgrade paths, we just see if
2022         # the common libstdc++.la exists in the ${LIBPATH} of the gcc that we are
2023         # unmerging.  if it does, that means this was a simple re-emerge.
2024
2025         # clean up the cruft left behind by cross-compilers
2026         if is_crosscompile ; then
2027                 if [[ -z $(ls "${ROOT}"/etc/env.d/gcc/${CTARGET}* 2>/dev/null) ]] ; then
2028                         rm -f "${ROOT}"/etc/env.d/gcc/config-${CTARGET}
2029                         rm -f "${ROOT}"/etc/env.d/??gcc-${CTARGET}
2030                         rm -f "${ROOT}"/usr/bin/${CTARGET}-{gcc,{g,c}++}{,32,64}
2031                 fi
2032                 return 0
2033         fi
2034
2035         # ROOT isnt handled by the script
2036         [[ ${ROOT} != "/" ]] && return 0
2037
2038         if [[ ! -e ${LIBPATH}/libstdc++.so ]] ; then
2039                 # make sure the profile is sane during same-slot upgrade #289403
2040                 do_gcc_config
2041
2042                 einfo "Running 'fix_libtool_files.sh ${GCC_RELEASE_VER}'"
2043                 /usr/sbin/fix_libtool_files.sh ${GCC_RELEASE_VER}
2044                 if [[ -n ${BRANCH_UPDATE} ]] ; then
2045                         einfo "Running 'fix_libtool_files.sh ${GCC_RELEASE_VER}-${BRANCH_UPDATE}'"
2046                         /usr/sbin/fix_libtool_files.sh ${GCC_RELEASE_VER}-${BRANCH_UPDATE}
2047                 fi
2048         fi
2049
2050         return 0
2051 }
2052
2053 do_gcc_config() {
2054         if ! should_we_gcc_config ; then
2055                 env -i ROOT="${ROOT}" gcc-config --use-old --force
2056                 return 0
2057         fi
2058
2059         local current_gcc_config="" current_specs="" use_specs=""
2060
2061         current_gcc_config=$(env -i ROOT="${ROOT}" gcc-config -c ${CTARGET} 2>/dev/null)
2062         if [[ -n ${current_gcc_config} ]] ; then
2063                 # figure out which specs-specific config is active
2064                 current_specs=$(gcc-config -S ${current_gcc_config} | awk '{print $3}')
2065                 [[ -n ${current_specs} ]] && use_specs=-${current_specs}
2066         fi
2067         if [[ -n ${use_specs} ]] && \
2068            [[ ! -e ${ROOT}/etc/env.d/gcc/${CTARGET}-${GCC_CONFIG_VER}${use_specs} ]]
2069         then
2070                 ewarn "The currently selected specs-specific gcc config,"
2071                 ewarn "${current_specs}, doesn't exist anymore. This is usually"
2072                 ewarn "due to enabling/disabling hardened or switching to a version"
2073                 ewarn "of gcc that doesnt create multiple specs files. The default"
2074                 ewarn "config will be used, and the previous preference forgotten."
2075                 use_specs=""
2076         fi
2077
2078         gcc-config ${CTARGET}-${GCC_CONFIG_VER}${use_specs}
2079 }
2080
2081 should_we_gcc_config() {
2082         # if the current config is invalid, we definitely want a new one
2083         # Note: due to bash quirkiness, the following must not be 1 line
2084         local curr_config
2085         curr_config=$(env -i ROOT="${ROOT}" gcc-config -c ${CTARGET} 2>&1) || return 0
2086
2087         # if the previously selected config has the same major.minor (branch) as
2088         # the version we are installing, then it will probably be uninstalled
2089         # for being in the same SLOT, make sure we run gcc-config.
2090         local curr_config_ver=$(env -i ROOT="${ROOT}" gcc-config -S ${curr_config} | awk '{print $2}')
2091
2092         local curr_branch_ver=$(get_version_component_range 1-2 ${curr_config_ver})
2093
2094         # If we're using multislot, just run gcc-config if we're installing
2095         # to the same profile as the current one.
2096         use multislot && return $([[ ${curr_config_ver} == ${GCC_CONFIG_VER} ]])
2097
2098         if [[ ${curr_branch_ver} == ${GCC_BRANCH_VER} ]] ; then
2099                 return 0
2100         else
2101                 # if we're installing a genuinely different compiler version,
2102                 # we should probably tell the user -how- to switch to the new
2103                 # gcc version, since we're not going to do it for him/her.
2104                 # We don't want to switch from say gcc-3.3 to gcc-3.4 right in
2105                 # the middle of an emerge operation (like an 'emerge -e world'
2106                 # which could install multiple gcc versions).
2107                 # Only warn if we're installing a pkg as we might be called from
2108                 # the pkg_{pre,post}rm steps.  #446830
2109                 if [[ ${EBUILD_PHASE} == *"inst" ]] ; then
2110                         einfo "The current gcc config appears valid, so it will not be"
2111                         einfo "automatically switched for you.  If you would like to"
2112                         einfo "switch to the newly installed gcc version, do the"
2113                         einfo "following:"
2114                         echo
2115                         einfo "gcc-config ${CTARGET}-${GCC_CONFIG_VER}"
2116                         einfo "source /etc/profile"
2117                         echo
2118                 fi
2119                 return 1
2120         fi
2121 }
2122
2123 #---->> support and misc functions <<----
2124
2125 # This is to make sure we don't accidentally try to enable support for a
2126 # language that doesnt exist. GCC 3.4 supports f77, while 4.0 supports f95, etc.
2127 #
2128 # Also add a hook so special ebuilds (kgcc64) can control which languages
2129 # exactly get enabled
2130 gcc-lang-supported() {
2131         grep ^language=\"${1}\" "${S}"/gcc/*/config-lang.in > /dev/null || return 1
2132         [[ -z ${TOOLCHAIN_ALLOWED_LANGS} ]] && return 0
2133         has $1 ${TOOLCHAIN_ALLOWED_LANGS}
2134 }
2135
2136 is_ada() {
2137         gcc-lang-supported ada || return 1
2138         use ada
2139 }
2140
2141 is_cxx() {
2142         gcc-lang-supported 'c++' || return 1
2143         ! is_crosscompile && tc_version_is_at_least 4.8 && return 0
2144         use cxx
2145 }
2146
2147 is_d() {
2148         gcc-lang-supported d || return 1
2149         use_if_iuse d
2150 }
2151
2152 is_f77() {
2153         gcc-lang-supported f77 || return 1
2154         use fortran
2155 }
2156
2157 is_f95() {
2158         gcc-lang-supported f95 || return 1
2159         use fortran
2160 }
2161
2162 is_fortran() {
2163         gcc-lang-supported fortran || return 1
2164         use fortran
2165 }
2166
2167 is_gcj() {
2168         gcc-lang-supported java || return 1
2169         use cxx && use_if_iuse gcj
2170 }
2171
2172 is_go() {
2173         gcc-lang-supported go || return 1
2174         use cxx && use_if_iuse go
2175 }
2176
2177 is_jit() {
2178         gcc-lang-supported jit || return 1
2179         use_if_iuse jit
2180 }
2181
2182 is_multilib() {
2183         tc_version_is_at_least 3 || return 1
2184         use multilib
2185 }
2186
2187 is_objc() {
2188         gcc-lang-supported objc || return 1
2189         use_if_iuse objc
2190 }
2191
2192 is_objcxx() {
2193         gcc-lang-supported 'obj-c++' || return 1
2194         use cxx && use_if_iuse objc++
2195 }
2196
2197 # Grab a variable from the build system (taken from linux-info.eclass)
2198 get_make_var() {
2199         local var=$1 makefile=${2:-${WORKDIR}/build/Makefile}
2200         echo -e "e:\\n\\t@echo \$(${var})\\ninclude ${makefile}" | \
2201                 r=${makefile%/*} emake --no-print-directory -s -f - 2>/dev/null
2202 }
2203
2204 XGCC() { get_make_var GCC_FOR_TARGET ; }
2205
2206 # The gentoo piessp patches allow for 3 configurations:
2207 # 1) PIE+SSP by default
2208 # 2) PIE by default
2209 # 3) SSP by default
2210 hardened_gcc_works() {
2211         if [[ $1 == "pie" ]] ; then
2212                 # $gcc_cv_ld_pie is unreliable as it simply take the output of
2213                 # `ld --help | grep -- -pie`, that reports the option in all cases, also if
2214                 # the loader doesn't actually load the resulting executables.
2215                 # To avoid breakage, blacklist FreeBSD here at least
2216                 [[ ${CTARGET} == *-freebsd* ]] && return 1
2217
2218                 want_pie || return 1
2219                 use_if_iuse nopie && return 1
2220                 hardened_gcc_is_stable pie
2221                 return $?
2222         elif [[ $1 == "ssp" ]] ; then
2223                 [[ -n ${SPECS_VER} ]] || return 1
2224                 use_if_iuse nossp && return 1
2225                 hardened_gcc_is_stable ssp
2226                 return $?
2227         else
2228                 # laziness ;)
2229                 hardened_gcc_works pie || return 1
2230                 hardened_gcc_works ssp || return 1
2231                 return 0
2232         fi
2233 }
2234
2235 hardened_gcc_is_stable() {
2236         local tocheck
2237         if [[ $1 == "pie" ]] ; then
2238                 if [[ ${CTARGET} == *-uclibc* ]] ; then
2239                         tocheck=${PIE_UCLIBC_STABLE}
2240                 else
2241                         tocheck=${PIE_GLIBC_STABLE}
2242                 fi
2243         elif [[ $1 == "ssp" ]] ; then
2244                 if [[ ${CTARGET} == *-uclibc* ]] ; then
2245                         tocheck=${SSP_UCLIBC_STABLE}
2246                 elif  [[ ${CTARGET} == *-gnu* ]] ; then
2247                         tocheck=${SSP_STABLE}
2248                 fi
2249         else
2250                 die "hardened_gcc_stable needs to be called with pie or ssp"
2251         fi
2252
2253         has $(tc-arch) ${tocheck} && return 0
2254         return 1
2255 }
2256
2257 want_minispecs() {
2258         if tc_version_is_at_least 4.3.2 && use hardened ; then
2259                 if ! want_pie ; then
2260                         ewarn "PIE_VER or SPECS_VER is not defined in the GCC ebuild."
2261                 elif use vanilla ; then
2262                         ewarn "You will not get hardened features if you have the vanilla USE-flag."
2263                 elif use nopie && use nossp ; then
2264                         ewarn "You will not get hardened features if you have the nopie and nossp USE-flag."
2265                 elif ! hardened_gcc_works ; then
2266                         ewarn "Your $(tc-arch) arch is not supported."
2267                 else
2268                         return 0
2269                 fi
2270                 ewarn "Hope you know what you are doing. Hardened will not work."
2271                 return 0
2272         fi
2273         return 1
2274 }
2275
2276 want_pie() {
2277         ! use hardened && [[ -n ${PIE_VER} ]] && use nopie && return 1
2278         [[ -n ${PIE_VER} ]] && [[ -n ${SPECS_VER} ]] && return 0
2279         tc_version_is_at_least 4.3.2 && return 1
2280         [[ -z ${PIE_VER} ]] && return 1
2281         use !nopie && return 0
2282         return 1
2283 }
2284
2285 has toolchain_death_notice ${EBUILD_DEATH_HOOKS} || EBUILD_DEATH_HOOKS+=" toolchain_death_notice"
2286 toolchain_death_notice() {
2287         if [[ -e "${WORKDIR}"/build ]] ; then
2288                 pushd "${WORKDIR}"/build >/dev/null
2289                 (echo '' | $(tc-getCC ${CTARGET}) ${CFLAGS} -v -E - 2>&1) > gccinfo.log
2290                 [[ -e "${T}"/build.log ]] && cp "${T}"/build.log .
2291                 tar jcf "${WORKDIR}"/gcc-build-logs.tar.bz2 \
2292                         gccinfo.log build.log $(find -name config.log)
2293                 rm gccinfo.log build.log
2294                 eerror
2295                 eerror "Please include ${WORKDIR}/gcc-build-logs.tar.bz2 in your bug report."
2296                 eerror
2297                 popd >/dev/null
2298         fi
2299 }