This is the mail archive of the
mailing list for the GCC project.
Re: Why is building a cross compiler "out-of-the-box" always broken?
OK, let me recap as I understand the discussion up to now, realizing
that this is the gcc list we can really only hope to fix things, if
needed, by making changes to the gcc project. Other project will have
It sounds like the consensus is that bootstrapping a cross-compiler
still requires the use of inhibit_libc and for a Linux target *should*
work like this. And, apparently is does work like this for some people
for some targets, just not for everyone for everything.
1. Configure the Linux kernel and "make headers_install".
2. Configure and make binutils using the headers produced in step 1.
3. Configure and make a minimal gcc cross-compiler for the target by
getting configure to set inhibit_libc and disabling any complicating
or conflicting options such as threads and multilib not strictly
needed to build the minimal compiler. This compiler should not be
generally used because of the restrictions placed on it during the
4. Use the minimal cross-compiler produced in step 3 to configure
glibc and do "make install-headers" to get glibc headers. At this
point you should be able to delete the minimal cross-compiler, it's
job has been done.
5. Make distclean and then configure, make, and install a normal gcc
cross-compiler for the target using the glibc headers produced in step 4.
6. Make distclean and then configure, make, and install the complete
glibc header and libraries etc. for the target.
7. Use the tools produced in steps 5 and 6 to do whatever
cross-compiling project you need them for.
Now for some thoughts about this. I assume we are working with current
releases of the kernel and tool chain. There are lots of problems with
various older combinations of things, let's not go there please right now.
1. Seems to be a good reliable source of sanitized headers for recent
kernels. I know of no problems with the current release.
2. Seems to build and work out-of-the-box using the headers from step
1. I know of no problems with current release.
3. Figuring out the correct combination of --with-newlib,
--with-sysroot, and --with-headers (or --without, or =no etc.) to get
inhibit_libc set and then figuring out which of the myriad of
--with-this-that-and-the-other options can or must be disabled to get
a functional minimal compiler is a real pain in the neck. Further
more, the make file may try (and fail) to make additional things like
crt0 in EXTRA_PARTS= which require the use of "make -k" and/or manual
copying of the needed bits and pieces. It does not always work and the
failures seem to be in different places on different targets. Maybe
the make files need to be modified some depending on the configure
setting of inhibit_libc?
If this is *supposed* to work, would it be worth while having a
--force-bootstrap or some such option so that configure could force
inhibit_libc and then short circuit lots of configuration stuff and
disable everything appropriate on a per-target basis so we can
reliably generate the minimal comiler needed for the next step? With
that, additional places in the source that really need inhibit_libc
special casing would be much clearer. Right now it's a question of
"wtf caused that to die?", since bootstrapping a cross-compiler is
such a black art to most people. Also, should the inhibit_libc hack
also disable things like the unwind support that requires kernel
headers? That not scrictly libc, but --without-headers sort of assume
neither are present. It would also be nice if there were a clear
statement about what needs to be where in the headers and/or sysroot
directory structures. Or, should be just require some sort of
combined tree build in this case? In which case it would be nice if
there were a clear statement about what needs to be copied or
symlinked from where to where to make it work. I'm a bit out of my
depth since I have *not* gotten it to work for many of the cases I
have tried, yet. It's not that I'm unwilling to try and contribute
patches, but I'd like to know where we are heading, please.
Some people advocate combining steps 3,4,5 by either cribbing a set of
headers from someone elses sysroot, cobbling them together by hand, or
by fooling glibc configure in to producing them without having a
minimal cross compiler. They build their cross-compiler using these
headers and then they proceed to step 6. That's great if you are only
working with one, common, target where you can expect to find someone
to crib from or you have better luck than I did trying to understand
and fool glibc configure. In any case that leaves us as the mercy of
changes to the glibc package, and the glibc maintainers can reasonably
assume the existance of a compiler and may use that compiler to check
things like sizeof(long double) etc. so it's fragile at best to rely
on. (BTW - why do we have both -m128bit-long-double and
-mlong-double-128 options for different targets?) However, it's
probably not viable for someone trying to build 20 or so tools chains
so they can check for kernel build failure tree wide etc. And
besides, it would sure be nice if gcc would build a cross-compiler
out-of-the-box if there is no problem with some other part of the tool
chain. That does not seem to be the case for all targets at this point.
Once you get to step 6, I expect you are home free, or at least are
out of the domain off gcc and need to talk to the glibc folks for any
problems that pop up at that point.
So, that's the situation as I see it. How should things work in an
ideal world and where do we go from here? Or, are other people happy
enough with the current ecosystem and think nothing needs to change?