public inbox for crossgcc@sourceware.org
 help / color / mirror / Atom feed
* --host versus --target
@ 2011-11-15 21:52 Trevor Woerner
  2011-11-15 22:45 ` Michael Hope
  2011-11-15 22:49 ` Yann E. MORIN
  0 siblings, 2 replies; 8+ messages in thread
From: Trevor Woerner @ 2011-11-15 21:52 UTC (permalink / raw)
  To: crossgcc

Hi,

In the crosstool-NG documentation is "5 - Using the toolchain.txt". In
there it recommends "using the target tuple to tell the build systems
to use your toolchain" and then gives an example of specifying the
'--target=tuple' option to 'configure'. Using crosstool-ng-1.13.1 I
recently built an arm-cortex_a8-linux-gnueabi toolchain. Looking
through the log file to see how, for example, strace was built for the
target I can't help notice --target was not used, only --host. I also
noticed that for all other tools --host is always specified.

I recently cross-compiled a system and never used --target, only
--host. Are there any definitive answers on how --target and --host
differ, or when they're needed (are they both needed, is only one
required)? I'm surprised my using --host seemed to have worked when
the documentation recommends --target.

I also was wondering about the --sysroot=<DIR> CFLAGS option. As I
successively compiled one package after another I kept installing them
to a staging area then copying them into one combined tree (with the
help of the populate script). Wouldn't it be necessary when
cross-compiling for a given target to keep specifying --sysroot=<DIR>
so the build machine's header files and libraries aren't accidentally
referenced during the build?

Best regards,
    Trevor

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-15 21:52 --host versus --target Trevor Woerner
@ 2011-11-15 22:45 ` Michael Hope
  2011-11-15 22:49 ` Yann E. MORIN
  1 sibling, 0 replies; 8+ messages in thread
From: Michael Hope @ 2011-11-15 22:45 UTC (permalink / raw)
  To: Trevor Woerner; +Cc: crossgcc

On Wed, Nov 16, 2011 at 10:51 AM, Trevor Woerner <twoerner@gmail.com> wrote:
> Hi,
>
> In the crosstool-NG documentation is "5 - Using the toolchain.txt". In
> there it recommends "using the target tuple to tell the build systems
> to use your toolchain" and then gives an example of specifying the
> '--target=tuple' option to 'configure'. Using crosstool-ng-1.13.1 I
> recently built an arm-cortex_a8-linux-gnueabi toolchain. Looking
> through the log file to see how, for example, strace was built for the
> target I can't help notice --target was not used, only --host. I also
> noticed that for all other tools --host is always specified.
>
> I recently cross-compiled a system and never used --target, only
> --host. Are there any definitive answers on how --target and --host
> differ, or when they're needed (are they both needed, is only one
> required)? I'm surprised my using --host seemed to have worked when
> the documentation recommends --target.

Hi Trevor.  The short answer is for most programs you set host to the
machine the program will run on, such as
--host=arm-cortex_a8-linux-gnueabi.  For unusual programs like GCC and
GDB where you run the program on x86 but target something else, you
use --host=x86... --target=arm-cortex_a8-linux-gnueabi.

So build==the machine used to build the program, host==the machine the
program runs on, and target==the machine the program works against.

-- Michael

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-15 21:52 --host versus --target Trevor Woerner
  2011-11-15 22:45 ` Michael Hope
@ 2011-11-15 22:49 ` Yann E. MORIN
  2011-11-16 16:16   ` Trevor Woerner
  1 sibling, 1 reply; 8+ messages in thread
From: Yann E. MORIN @ 2011-11-15 22:49 UTC (permalink / raw)
  To: crossgcc; +Cc: Trevor Woerner

Trevor, All,

On Tuesday 15 November 2011 22:51:55 Trevor Woerner wrote:
> In the crosstool-NG documentation is "5 - Using the toolchain.txt". In
> there it recommends "using the target tuple to tell the build systems
> to use your toolchain" and then gives an example of specifying the
> '--target=tuple' option to 'configure'. Using crosstool-ng-1.13.1 I
> recently built an arm-cortex_a8-linux-gnueabi toolchain. Looking
> through the log file to see how, for example, strace was built for the
> target I can't help notice --target was not used, only --host. I also
> noticed that for all other tools --host is always specified.

Right, this is incorrect. This should be:
  ./configure --build=(build-tuple) --host=your-target-tuple

> I recently cross-compiled a system and never used --target, only
> --host. Are there any definitive answers on how --target and --host
> differ, or when they're needed (are they both needed, is only one
> required)? I'm surprised my using --host seemed to have worked when
> the documentation recommends --target.

The documentation is wrong, that's why! :-)

In the very beginnings, eons ago, autotools also got confused by this
whole build vs. host vs. target, and got it wrong. Now they fixed it,
but they want to keep backward compatibility, so the --target is still
recongised, although ./configure will complain if you do so.

So yes, --host is what you want. You should also pass --build, for
completeness...

> I also was wondering about the --sysroot=<DIR> CFLAGS option. As I
> successively compiled one package after another I kept installing them
> to a staging area then copying them into one combined tree (with the
> help of the populate script). Wouldn't it be necessary when
> cross-compiling for a given target to keep specifying --sysroot=<DIR>
> so the build machine's header files and libraries aren't accidentally
> referenced during the build?

There are three schools of thought here:

1) Those who want to install directly in the sysroot of the toolchain.
   Their argument is that the compiler will automagically find headers
   and libraries without extra flags.
   This means that the toolchain gets poluted, and can not be re-used.

2) Those who copy the toolchain's sysroot to a 'staging' area, where they
   install everything, and they pass --sysroot=staging to the compiler, so
   it automagically finds headers and libs.
   It's a viable option, but forces to always force CFLAGS to include
   --sysroot=staging, or requires the use of a wrapper to a few select
   tools (gcc, ld...) to pass this flag.
   That's what buildroot does using a wrapper, when using an external
   toolchain.

3) Those that use a staging area to install programs, but do not pre-fill
   that staging with the sysroot. They have to pass appropriate CPPFLAGS
   and LDFLAGS to tell the compiler where to find non-system headers and
   libs, or use a wrapper to a few select tools (gcc, ld...) to pass those
   flags.

I'm in favor of 3) but I have no strong opinion against 2) either; both
maitain the 'purity' of the toolchain. 1) is purely horrible, as the
toolchain gets polluted, and can not be re-used.

There's a 4th alternative, which is a bit more involved:

4) A mix of 2) and 3), using carefully crafted union mounts. The staging
   area is a union mount of:
     - the sysroot as a read-only branch,
     - the real staging area as a read-write branch
   This also requires passing --sysroot to point to the union mount, but
   has other advantages, such as allowing per-package staging, and a few
   more obscure pros. It also has its disadvantages, as it requires the
   possibility for non-root users to create union mounts; union mounts
   are not yet mainstream in the Linux kernel, so it requires patching;
   there is a FUSE-based unionfs implementation, but development is almost
   stalled, and there are a few gotchas...

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-15 22:49 ` Yann E. MORIN
@ 2011-11-16 16:16   ` Trevor Woerner
  2011-11-16 18:13     ` Yann E. MORIN
  2011-11-17 19:23     ` Thomas Petazzoni
  0 siblings, 2 replies; 8+ messages in thread
From: Trevor Woerner @ 2011-11-16 16:16 UTC (permalink / raw)
  To: crossgcc

Thank you, Michael and Yann, for the quick and detailed responses!

I wasn't aware there existed different strategies for putting together
a cross-root-filesystem, I'm quite happy you took the time to list
them. Ironically, looking through the list (and I realize you're not
going to agree) I think option #1 is the best. Having recently put in
the time to put together such an image, I can attest it was quite a
pain getting the various packages to compile correctly. If I was
_really_ lucky, what I was trying to compile would have autotools
support, but even then CFLAGS would often not be handled correctly. So
specifying a value for CFLAGS on the cmdline would often clobber flags
the package needed to compile correctly. Then, I would often
additionally need to specify "-L" options so the linker so it could
find the libraries against which I wanted to link (why the link step
wouldn't work even though I was providing --sysroot is a bit of a
mystery still). If the package used C++ I would then have to
determine/guess if I needed to use CPPFLAGS, CXXFLAGS, or CCFLAGS.

I can appreciate you have your reasons for not liking option 1, but
from my point of view: for what other purpose does the cross-compiler
exist other than to create a cross-filesystem? It's not like I'm going
to then use the cross-compiler to cross-compile random bits and pieces
which aren't going to be put on the image anyway, so preserving its
integrity is irrelevant to me. Besides, for all the effort and
trail-and-error it would save me, I'd rather just rebuild the cross
toolchain and have multiple copies of it installed on my development
machine if I needed a pristine one or was putting together multiple
images. I'm guessing there are probably other reasons?

I'm assuming, however, to use option 1 I would need to specify the
toolchain's sysroot directory as the --prefix? Won't that mess up the
dynamic loader on the target (although if all libraries are installed
to $SYSROOT/lib and $SYSROOT/usr/lib I'm guessing it'll just work)?

Best regards,
    Trevor

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-16 16:16   ` Trevor Woerner
@ 2011-11-16 18:13     ` Yann E. MORIN
  2011-11-16 20:18       ` Trevor Woerner
  2011-11-17 19:23     ` Thomas Petazzoni
  1 sibling, 1 reply; 8+ messages in thread
From: Yann E. MORIN @ 2011-11-16 18:13 UTC (permalink / raw)
  To: crossgcc; +Cc: Trevor Woerner

Trevor, All,

On Wednesday 16 November 2011 17:16:08 Trevor Woerner wrote:
> I can appreciate you have your reasons for not liking option 1, but
> from my point of view: for what other purpose does the cross-compiler
> exist other than to create a cross-filesystem? It's not like I'm going
> to then use the cross-compiler to cross-compile random bits and pieces
> which aren't going to be put on the image anyway, so preserving its
> integrity is irrelevant to me. Besides, for all the effort and
> trail-and-error it would save me, I'd rather just rebuild the cross
> toolchain and have multiple copies of it installed on my development
> machine if I needed a pristine one or was putting together multiple
> images. I'm guessing there are probably other reasons?

Yes, a toolchain that is shared betwen many developpers. For example,
consider this situation:
 - 10+ hardware targets, of different architectures (ARM, x86, MIPS...)
 - 50+ projects
 - team of 150+ developpers
 - team dedicated to the tooling (toolchains, build system...)

In that situation, you want to ensure all developpers have the same tools
for a given tuple {project,target}, but you can't replicate the toolchains
for every developpers, or upgrades would be a ultimate burden. Also, you
do not want to allow each developper to fiddle with the toolchain, or it
would no longer be the same toolchain other developpers are using.

So, you do not want the toolchain sysroot to be polluted with what every
developer wants to install on his rootfs.

Yes, this is a common situation in an industrial context...

> I'm assuming, however, to use option 1 I would need to specify the
> toolchain's sysroot directory as the --prefix?

No, you want to set prefix to the _runtime_ prefix, probably / or /usr or
/usr/local. And you want to use: make DESTDIR=/path/to/staging install.

> Won't that mess up the
> dynamic loader on the target (although if all libraries are installed
> to $SYSROOT/lib and $SYSROOT/usr/lib I'm guessing it'll just work)?

The problem will not be, in the common case, with the dynamic linker.
ELF headers only list the name of the libraries to load, not their paths,
so the dynamic linker will succesfuly find libraries at runtime.

The problem will arise when programs will try to load their data, because
they were configured to expect everything in (say) /home/foo/blabla/sysroot
but this path does not exist at runtime, so they would fail to load:
 - their ressources (icons, images...)
 - their dlopen-ed libraries
 - the libraries in RPATH (RPATH is a beast to deal with, though with a bit
   of fiddling, it can be made to behave)

So what you want to do, is:
  ./configure --build=build-tuple --host=host-tuple    \
              --prefix=/usr --enable-foo-bar...
  make
  make DESTDIR=/path/to/staging install

and repeat for all your packages. Then if you used the sysroot as staging,
you'd have to push that to the target rootfs (eg. filesystem image, copy
to NFSroot...), but you would endup with lots of cruft: headers, static
libs, many other things that makes the sysroot usefull at build time, but
are mostly useless at runtime. Then you'd have to clean it up. Basically,
about 75% (size wise) of a uClibc sysroot is useless at runtime (32MiB, vs.
only 8MiB for all .so files). It's even worse with glibc.

With the third alternative, you only have to copy the _required_ files
from the sysroot to the staging, by scanning all ELF files from your
staging, on fetching the NEEDED files from the sysroot. Crostool-NG
installs a program that does just that: tuple-populate

Of course, it means you indeed have to pass appropriate CPPFLAGS to point
to where your non-sysroot headers are, and proper LDFLAGS to where non-
sysroot libraries are, eg.:
    CPPFLAGS="-I/path/to/staging/usr/include"                       \
    LDFLAGS="-L/path/to/staging/lib -L/path/to/staging/usr/lib"     \
    ./configure blabla-as-above...

Solution two would mean:
    cp -a $(tuple-gcc --your-cflags-except-sysroot -print-sysroot)  \
       /path/to/staging
    ./configure --blabla-as-above                                  \
                CC="tuple-gcc --syroot=/path/to/staging"           \
                CXX="tuple-g++ --sysroot=/path/to/staging"         \
                LD="tuple-ld --sysroot=/path/to/staging"           \
                AND_SO_ON=tuple-andsoon --sysroot=/path/to/staging"

Or you would need to provide a wrapper to gcc, and still tell configure
where to find it... Sigh, that's not easy...

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-16 18:13     ` Yann E. MORIN
@ 2011-11-16 20:18       ` Trevor Woerner
  2011-11-16 22:43         ` Yann E. MORIN
  0 siblings, 1 reply; 8+ messages in thread
From: Trevor Woerner @ 2011-11-16 20:18 UTC (permalink / raw)
  To: crossgcc

Yann,

On Wed, Nov 16, 2011 at 1:12 PM, Yann E. MORIN
<yann.morin.1998@anciens.enib.fr> wrote:
>> I'm assuming, however, to use option 1 I would need to specify the
>> toolchain's sysroot directory as the --prefix?
>
> No, you want to set prefix to the _runtime_ prefix, probably / or /usr or
> /usr/local. And you want to use: make DESTDIR=/path/to/staging install.

Thank you, now I understand.

I had been under the mistaken assumption that the cross-compiler would
perform its #include search with the host system's /usr/include
(etc...) by default (just like my system's native compiler). If that
were the case I would have to somehow tell the compiler to change its
behaviour, which I guessed could be done via ./configure's --prefix
option. But by playing with the cross-compiler's "-v" option I can see
that it instead looks in all the proper locations for the
cross-toolchain's #include files without considering the host system's
default locations:

#include "..." search starts here:
#include <...> search starts here:
<ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/include
<ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/include-fixed
<ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/../../../../i686-nptl-linux-gnu/include
<ct-ng install path>/i686-nptl-linux-gnu/sysroot/usr/include

This is good news because it means I don't have to do anything
explicitly (although its implicit nature confused me) other than to
inform the compiler of the location of any staging directories. It
also means that both the compiles which take place as part of the
./configure as well as the compiles which are done as part of the
build itself (and any compiles that sometimes occur during an
install!) will behave correctly.

Just out of curiosity, why is the cross-compiler behaving this way
(i.e. why isn't it searching for #includes in the system's
/usr/include directory)? Is it because it is a cross-compiler, or
because it is a sysroot'ed cross-compiler, or because it is performing
a cross-compile? I noticed, while looking through the "-v" output that
someone is including a --sysroot option implicitly.

Thank you for the detailed explanation of how to work each option (in
addition to listing the options previously).

> Solution two would mean:
>    cp -a $(tuple-gcc --your-cflags-except-sysroot -print-sysroot)  \
>       /path/to/staging
>    ./configure --blabla-as-above                                  \
>                CC="tuple-gcc --syroot=/path/to/staging"           \
>                CXX="tuple-g++ --sysroot=/path/to/staging"         \
>                LD="tuple-ld --sysroot=/path/to/staging"           \
>                AND_SO_ON=tuple-andsoon --sysroot=/path/to/staging"

Very nice, I like this trick (of including the --sysroot as part of
the tool command)! It would save me from caring whether the build
system that comes with the software package handles
CFLAGS/CXXFLAGS/CPPFLAGS/etc... correctly.

Best regards,
    Trevor

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-16 20:18       ` Trevor Woerner
@ 2011-11-16 22:43         ` Yann E. MORIN
  0 siblings, 0 replies; 8+ messages in thread
From: Yann E. MORIN @ 2011-11-16 22:43 UTC (permalink / raw)
  To: crossgcc; +Cc: Trevor Woerner

Trevor, All,

On Wednesday 16 November 2011 21:18:07 Trevor Woerner wrote:
> playing with the cross-compiler's "-v" option I can see
> that it instead looks in all the proper locations for the
> cross-toolchain's #include files without considering the host system's
> default locations:
> 
> #include "..." search starts here:
> #include <...> search starts here:
> <ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/include
> <ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/include-fixed
> <ct-ng install path>/lib/gcc/i686-nptl-linux-gnu/4.5.2/../../../../i686-nptl-linux-gnu/include
> <ct-ng install path>/i686-nptl-linux-gnu/sysroot/usr/include
[--SNIP--]
> Just out of curiosity, why is the cross-compiler behaving this way
> (i.e. why isn't it searching for #includes in the system's
> /usr/include directory)? Is it because it is a cross-compiler, or
> because it is a sysroot'ed cross-compiler, or because it is performing
> a cross-compile?

All of that.

Because it is a cros-compiler, it is smart enough to not look for the
host (the host of the toolchain!) headers and libs, but in a specific
location specified at compile time (compile time of the toolchain!).

That location is what we call the sysroot. The sysroot was introduced
like 6-7 years ago IIRC. Before that, that location was not named
sysroot, although it did exist. But the gcc was not relocatable, and
there were other minor twists, but it's kind of blurry in my head.

Now, we have sysrooted toolchains. These are marvelous beasts, such that
if gcc is configured with a sysroot that is a sub-dir of its install
prefix, then the user can move the (full) toolchain to another directory,
and gcc will automagically find the new location of the sysroot! Magic! :-)

Non-sysrooted toolchains belong to the past, and they should not ever be
allowed to wander our Earth any more! :-)

> I noticed, while looking through the "-v" output that
> someone is including a --sysroot option implicitly.

That must be gcc calling ld.

The trick is, there can be more than one sysroot in a toolchain; gcc can
use some of its flags (eg. big/little endian, -march and so on...) to
select one sysroot or the other. This is called a multilib toolchain.
So, gcc has to tell ld what sysroot to use.

Although crosstool-NG is not yet capable of building multilib toolchains,
gcc has no way of knowing that there's only one sysroot, so it always
tells ld what sysroot to use, even if it's the default one.

(Well, there is a very promising patch recently submitted to support
multilib, but it needs some refreshing first).

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: --host versus --target
  2011-11-16 16:16   ` Trevor Woerner
  2011-11-16 18:13     ` Yann E. MORIN
@ 2011-11-17 19:23     ` Thomas Petazzoni
  1 sibling, 0 replies; 8+ messages in thread
From: Thomas Petazzoni @ 2011-11-17 19:23 UTC (permalink / raw)
  To: crossgcc

Le Wed, 16 Nov 2011 11:16:08 -0500,
Trevor Woerner <twoerner@gmail.com> a écrit :

> I wasn't aware there existed different strategies for putting together
> a cross-root-filesystem, I'm quite happy you took the time to list
> them. Ironically, looking through the list (and I realize you're not
> going to agree) I think option #1 is the best. Having recently put in
> the time to put together such an image, I can attest it was quite a
> pain getting the various packages to compile correctly.

That's because you shouldn't be doing that manually. There are embedded
Linux build systems that are designed to precisely handle this work.
OpenEmbedded, Yocto, Buildroot, PTXdist, OpenBricks, etc. My preference
of course goes towards Buildroot, since I'm part of the development
team. But the others are fine, too, since they make this
cross-compilation easier *and* reproducible.

Handling the cross-compilation of the various packages for its embedded
Linux system in a manual way is a very bad development practice, in my
opinion.

Best regards,

Thomas
-- 
Thomas Petazzoni, Free Electrons
Kernel, drivers, real-time and embedded Linux
development, consulting, training and support.
http://free-electrons.com

--
For unsubscribe information see http://sourceware.org/lists.html#faq

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2011-11-17 19:23 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-11-15 21:52 --host versus --target Trevor Woerner
2011-11-15 22:45 ` Michael Hope
2011-11-15 22:49 ` Yann E. MORIN
2011-11-16 16:16   ` Trevor Woerner
2011-11-16 18:13     ` Yann E. MORIN
2011-11-16 20:18       ` Trevor Woerner
2011-11-16 22:43         ` Yann E. MORIN
2011-11-17 19:23     ` Thomas Petazzoni

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).