Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Sauermann J.Realtime operating systems.Concepts and implementation of microkernels for embedded systems.1997.pdf
Скачиваний:
27
Добавлен:
23.08.2013
Размер:
1.32 Mб
Скачать

112

6.4 Building the Cross-Environment

 

 

6.4Building the Cross-Environment

In the following, we assume that the cross-environment is created in a directory called /CROSS on a UNIX or Linux host, which is also the build machine. In order to perform the “ make install” steps below, you either need to be root or the /CROSS directory exists and you have write permission for it.

Since we assume a MC68020 CPU for the embedded system, we choose a sun3 machine as target. This machine has a CPU of the MC68000 family and is referred to as m68k-sun-sunos4.1 when specifying targets. The general name for a target has the form CPU-Manufacturer-OperatingSystem.

For a DOS host, please follow the installation instructions provided with the binutils and gcc packages instead.

6.4.1 Building the GNU cross-binutils package

The GNU binutils package contains a collection of programs, of which some are essential. The absolute minimum required is the cross-assembler as (which is required by the GNU C++ cross-compiler) and the cross-linker ld. The Makefile provided in this book also uses the cross-archive program ar, the name utility nm and the objcopy program.

1# Makefile for gmake

2#

3

4# Development environment.

5# Replace /CROSS by the path where you installed the environment

6#

7

AR

:= /CROSS/bin/m68k-sun-sunos4.1-ar

8

AS

:= /CROSS/bin/m68k-sun-sunos4.1-as

9

LD

:= /CROSS/bin/m68k-sun-sunos4.1-ld

10

NM

:= /CROSS/bin/m68k-sun-sunos4.1-nm

11

OBJCOPY

:= /CROSS/bin/m68k-sun-sunos4.1-objcopy

12

CC

:= /CROSS/bin/m68k-sun-sunos4.1-gcc

13

MAKE

:= gmake

Since the Makefile provided with the binutils package builds all these programs by default, there is no use at all to build only particular programs instead of the complete binutils suite.

To install the GNU binutils package, proceed as follows:

Get hold of a file called binutils-2.8.1.tar.gz and store it in a separate directory, for instance /CROSS/src. You can get this file either from a CDROM, e.g. from a Linux distribution, or from the WWW: ftp://prep.ai.mit.edu/pub/gnu/binutils-2.8.1.tar.gz or

or
if your tar program does not support the -z option

6. Development Environment

113

 

 

ftp://ftp.funet.fi/pub/gnu/gnu/binutils-2.8.1.tar.gz

In the /CROSS/src directory, unpack the file: > cd /CROSS/src

> tar -xvzf binutils-2.8.1.tar.gz

> zcat binutils-2.8.1.tar.gz | tar -xvf -

Change to the directory created by the tar program: > cd binutils-2.8.1

Read the file README for instructions particular for your host

Configure the package. There is a period of a few minutes during which no screen output is generated. If your build machine is not the host, you need

to specify a --host= option as well:

> ./configure

--target=m68k-sun-sunos4.1 \

>

--enable-targets=m68k-sun-sunos4.1 \

 

--prefix=/CROSS

Build the packet, which takes about 20 minutes:

>gmake all-gcc

Install the packet, either as root or with write permission to /CROSS.

>gmake install

6.4.2 Building the GNU cross-gcc package

To install the GNU gcc package, proceed as follows:

Get hold of a file called gcc-2.8.1.tar.gz and store it in a separate directory, for instance. /CROSS/src. You can get this file either from a CD-ROM, e.g. from a Linux distribution, or from the WWW: ftp://prep.ai.mit.edu/pub/gnu/gcc-2.8.1.tar.gz or ftp://ftp.funet.fi/pub/gnu/gnu/gcc-2.8.1.tar.gz

In the /CROSS/src directory, unpack the file: > cd /CROSS/src

> tar -xvzf gcc-2.8.1.tar.gz

or

> zcat gcc-2.8.1.tar.gz | tar -xvf -

if your tar program does not

 

support the -z option

Change to the directory created by the tar program: > cd gcc-2.8.1

Read the file INSTALL for instructions particular for your host

Configure the package. If your build machine is not the host, you need to specify a --host= option as well:

> ./configure

--target=m68k-sun-sunos4.1 \

 

--prefix=/CROSS \

114

6.4 Building the Cross-Environment

 

 

--with-gnu-ld \ --with-gnu-as

Build the C and C++ compilers, which takes about 30 minutes. This make is supposed to fail when making libgcc1.cross. This is on purpose, since we have not supplied a libgcc1.a at this point:

>make LANGUAGES=”C C++”

Install the compilers, either as root or with write permission to /CROSS:

>make LANGUAGES=”c c++” install-common

>make LANGUAGES=”c c++” install-driver

You may optionally install man pages and/or info files as root:

>make LANGUAGES=”c c++” install-man

>make LANGUAGES=”c c++” install-info

Note: There are some dependencies between the actual gcc compiler version and the libgcc.a library used with it. There are also dependencies between the compiler version and the source code for the target, in particular regarding template class instantiation and support for C++ exceptions. It might therefore be necessary to change the source code provided in this book for different compiler versions.

6.4.3 The libgcc.a library

The gcc compiler requires a library that contains functions generated by the compiler itself. This library is usually called libgcc.a. The default installation procedure of gcc requires that a library libgcc1.a is provided beforehand and creates another library libgcc2.a itself. These two libraries libgcc1.a and libgcc2.a are then merged into the library libgcc.a. Since we have not provided a libgcc1.a, the build was aborted when building the make target libgcc1.cross as described in Section 6.4.2. The difference between libgcc1.a and libgcc2.a (besides the fact that they contain entirely different functions) is that libgcc2.a can be compiled with gcc, while libgcc1.a functions usually cannot, at least not without in-line assembly code.

The final step in setting up the cross-environment is to create libgcc.a:

Change to the gcc build directory:

>cd /CROSS/gcc-2.8.1

Build the libgcc2 library:

>make LANGUAGES=”c c++” libgcc2.a

Rename libgcc2.a to libgcc.a:

>mv libgcc2.a libgcc.a

6. Development Environment

115

 

 

At this point, you have a libgcc.a, but it still lacks the functions of libgcc1.a . The functions in libgcc1.a provide multiplication, division, and modulo operations for 32 bit and 64 bit integers. For the MC68020 and higher CPUs, these operations are directly supported by the CPU, and the gcc will use them if the -mc68020 flag is present. In this case, there is nothing more to do and you may decide to leave the libggc.a as it is. If you do so, you should always check the final Target.td file for undefined symbols.

If you want to do it the proper way because you do not have a MC68020 CPU, or if you want to make sure that your cross-environment works under all circumstances, you have to provide the functions for libgcc1.a yourself. In order to get them compiled with gcc, you are of course not allowed to use the functions you are implementing.

As an example, we consider the function _mulsi3, which is supposed to multiply two signed 32 bit integers and to return the result. You may implement it as follows (not tested): ??? sollte das nicht besser doch getested sein ???

long _mulsi3(long p1, long p2)

{

long result;

int negative = 0;

if (p1 < 0) { p1 = -p1; negative++; } if (p2 < 0) { p2 = -p2; negative++; }

asm("

 

 

MOVE.L %1,D1

| D1.L == p1

MOVE.L %2,D2

| D2.L == p2

MOVE.W D2,D0

| D0.W == p1_low

MULU

D1,D0

| D0.L == p1_low * p2_low

MOVE.L

D2,D3

| D3.L == p2

SWAP

D3

| D3.W == p2_high

MULU

D1,D3

| D3.L == p1_low * p2_high

SWAP

D1

| D1.W == p1_high

MULU

D2,D1

| D1.L == p1_high * p2_low

ADD.L

D1,D3

| D3.L == p1_low * p2_high + p1_high * p2_low

SWAP

D3

| shift D3.L 16 bits, D3.W dirty

CLR.W

D3

| D3.L == (p1_low * p2_high + p1_high * p2_low) << 16

ADD.L

D3,D0

| D0.L == p1 * p2

MOVE.L

D0,%0

| store result

" : =g(result) : "g"(p1), "g"(p2) : "d0", "d1", "d2", "d3" );

if (negative & 1)

return -result;

else

 

return result;

}

The libgcc.a contains several modules for C++ exception support. For an embedded system, you will most probably not use any exceptions at all, since exceptions are fatal errors in this context. When compiling C++ programs, the gcc enables exception processing by default. This will increase the size of the ROM image by about 9 kilobytes, which is slightly less than the whole operating system

116

6.4 Building the Cross-Environment

 

 

without applications. You should therefore disable exception handling with the gcc option -fno-exceptions.