Update from Pedro Romano <pmcnr@camoes.rnl.ist.utl.pt>.

This commit is contained in:
Joel Sherrill
1998-04-27 18:42:04 +00:00
parent 0c508af979
commit 96d56b3690
12 changed files with 312 additions and 844 deletions

View File

@@ -1,37 +1,87 @@
#
# $Id$
#
Joel's Note: +-----------------------------------------------------------------------------+
| RTEMS 4.0.0 PC386 BSP HOWTO - 1998/04/21 |
+-----------------------------------------------------------------------------+
| (C) Copyright 1998 - |
| - NavIST Group - Real-Time Distributed Systems and Industrial Automation |
| |
| http://pandora.ist.utl.pt |
| |
| Instituto Superior Tecnico * Lisboa * PORTUGAL |
+-----------------------------------------------------------------------------+
| Disclaimer: |
| |
| This file is provided "AS IS" without warranty of any kind, either |
| expressed or implied. |
+-----------------------------------------------------------------------------+
This has some information which is specific to 3.6.0. Other parts of the
document should be merged with the main RTEMS READMEs. Procedures for
building a boot floppy, from a network server, and other information
specific to this BSP should remain in this file.
-----------
RTEMS PC386 BSP HOWTO:
1. Introduction 1. Introduction
--------------- ---------------
This howto tries to explain how to setup the RTEMS host This tries to explain how to setup the RTEMS host environment so
environment on a Linux based PC so that RTEMS applications can be that RTEMS applications can be built for and run in a bare PC 386 or
built for and run in a bare PC 386+. above.
It covers essentially the aspects of loading images, since
information concerning other issues such as building the development
tools and the RTEMS distribution can be found in the 'RTEMS 4.0.0
On-Line Library' under 'Getting Started with RTEMS for C/C++ Users'.
Please note that everything in the following text using the Please note that everything in the following text using the
notation '<...>' is just an alias to something and should always be notation '<...>' is just an alias to something and should always be
substituted by the real thing! substituted by the real thing!
2. Unarchiving
2. Building the GNU C/C++ Cross Compiler Toolset
------------------------------------------------
Obtaining, building and installing the tools for building the
PC386 BSP of RTEMS is covered in detail in the 'RTEMS 4.0.0 On-Line
Library' -> 'Getting Started with RTEMS for C/C++ Users' -> 'Building
the GNU C/C++ Cross Compiler Toolset'.
When running the 'bit' script you should use the 'i386-elf'
configuration.
4. Building RTEMS
-----------------
Obtaining, building and installing the tools for building the
PC386 BSP is covered in detail in the 'RTEMS 4.0.0 On-Line Library' ->
'Getting Started with RTEMS for C/C++ Users' -> 'Building RTEMS'.
When running configure, use the following values for the listed
options:
--target=i386-rtems
--enable-rtemsbsp=pc386
--prefix=i386-rtems
5. RTEMS Tests
-------------- --------------
Files which have been "tarred, zipped" (i.e. .tar.gz or .tgz If you've completed the last step successfully, you'll find the
RTEMS sample and test files that can be loaded with GRUB in the
'<build_point>/pc386/tests' directory, RTEMS sample and test files in
a format suitable for use with NetBoot in the
'<build_point>/pc386/BootImgs' directory.
6. Loading RTEMS PC386 applications
-----------------------------------
6.1. Unarchiving
----------------
Files which have been "tarred, gzipped" (i.e. .tar.gz or .tgz
extension) may be unarchived with a command similar to one of the extension) may be unarchived with a command similar to one of the
following: following:
gzcat <file>.tgz | tar xvof - zcat <file>.tgz | tar xvof -
OR OR
@@ -39,455 +89,215 @@ following:
OR OR
gtar xzvf <file>.tgz tar xzvf <file>.tgz
NOTE: gunzip -c is equivalent to gzcat, while gtar is GNU tar. NOTE: gunzip -c is equivalent to zcat. On commercial (non-Linux)
Unices, since the GNU utilities are not the standard 'tar' will be
gtar (GNU tar) and 'zcat' will be 'gzcat'.
Given that the necessary utility programs are installed, any of Given that the necessary utility programs are installed, any of
the above commands will extract the contents of <file>.tar.gz into the the above commands will extract the contents of <file>.tar.gz into the
current directory. All of the RTEMS components will be extracted into current directory. To view the contents of an archive without
the subdirectory rtems-3.2.0. To view the contents of a component restoring any files, use a command similar to the following:
without restoring any files, use a command similar to the following:
gzcat <file>.tgz | tar tvf -
3. The building tools (gcc, binutils, et al.) zcat <file>.tgz | tar tvf -
---------------------------------------------
The PC386 BSP was developed so that the Linux native building
tools can be used to build the RTEMS binaries.
With this in mind all you have to do is check if you have gcc +
binutils (as, ld, ar, objcopy) installed in your system (which most
probably you'll have) and check their versions. You can do so with:
- 'gcc -v' (for gcc); --> version 2.7.2.1
- 'ld -v' (for binutils). --> version 2.8.1 (with BFD linux-2.8.1.0.1)
The above mentioned versions of gcc and binutils are almost 6.2 Using GRUB to load RTEMS PC386 applications
certainly guaranteed to work (their the ones we've been using). More -----------------------------------------------
recent versions should also be ok, and older versions may be ok too.
The only known problem is with older versions of binutils which Using GRUB (GRand Unified Bootloader) is the simplest way to load
still don't have a 'binary' target in 'objcopy'. We need objcopy's and run your PC386 BSP samples, tests and programs.
binary target to produce our final binaries (this will probably be
enhanced in the future, so we get them directly from the 'elf32-i386'
object, but for now this is how we do it). There's a possible
workaround this, using older versions of 'objdump' with the flags used
to produce the Linux kernel binary. You can investigate this in the
Linux source makefiles. This hasn't been tested.
It should be ok to build a cross-compilation environment (gcc + You can get the latest release of GRUB from its homepage:
binutils) that supports the 'elf32-i386' target, so that you can use a
host system other than Linux. This hasn't been tested.
You can get 'gcc' and 'binutils', both pre-compiled binaries for - http://www.uruk.org/grub/
Linux and sources from:
ftp://sunsite.unc.edu/pub/Linux/GCC/ or alternatively by ftp from:
binutils-2.8.1.0.1.bin.tar.gz - ftp://ftp.uruk.org/public/grub/
binutils-2.8.1.0.1.tar.gz
gcc-2.7.2.1.bin.tar.gz
as well as from several other mirrors and sites. Once you obtain the .tar.gz archive 'grub-0.4.tar.gz', change to a
temporary directory (you won't need the grub files after this and can
just go ahead and delete the whole directory structure that was
generated) and unarchive 'grub-0.4.tar.gz' following the instructions
given above in [2. Unarchiving].
4. Creating aliases for gcc and the binutils After this is done change the directory to:
--------------------------------------------
The NEWLIB expects to be compiled by a cross-compiler. The easiest grub-0.4/bin_std
(as far as we could find out) way to do this, short of changing the
configuration files is to make symbolic links from cross-compiler
style names (the usual names with a 'i386-elf32-rtems-' prefix) to the
real name.
You can use the following shell script to create these links and there you'll find the two files you'll need from this archive:
quickly. It assumes that the native Linux 'gcc' and 'binutils' reside 'stage1' and 'stage2'.
in their usual place (i.e. '/usr/bin/'). It also assumes that you're
running it in the directory where the aliases will reside (which we
will refer to as <elf32-tools>). You should then add <elf32-tools> to
you path. This is necessary for building the NEWLIB package.
--- CUT HERE --- CUT HERE --- CUT HERE --- CUT HERE --- CUT HERE --- You should have two (2) formatted diskettes available. One of
these will only be used temporarily to create the other one, and we'll
refer to it as 'RAW GRUB' diskette (you can label it accordingly if
you wish). The other diskette, which we will refer to as 'GRUB FS'
should be high-level formatted with one of GRUB's supported file
systems, which are: DOS FAT, BSD FFS, and Linux ext2fs.
#!sh A DOS FAT diskette can, obviously, be created under DOS with the
ln -sf /usr/bin/ar i386-elf32-rtems-ar 'FORMAT' command. Under Linux, the following commands are available to
ln -sf /usr/bin/as i386-elf32-rtems-as add file systems to low-level formatted diskettes:
ln -sf /usr/bin/cpp i386-elf32-rtems-cpp
ln -sf /usr/bin/gasp i386-elf32-rtems-gasp
ln -sf /usr/bin/gcc i386-elf32-rtems-gcc
ln -sf /usr/bin/ld i386-elf32-rtems-ld
ln -sf /usr/bin/objcopy i386-elf32-rtems-objcopy
ln -sf /usr/bin/objdump i386-elf32-rtems-objdump
ln -sf /usr/bin/ranlib i386-elf32-rtems-ranlib
--- CUT HERE --- CUT HERE --- CUT HERE --- CUT HERE --- CUT HERE --- 1. To add a DOS FAT file system to a low-level formatted diskette:
5. Building Newlib
------------------
The next step is to build and install the NEWLIB package. The a) If you have mtools installed:
version we've been using and have tested is:
newlib-1.7.0-posix-rtems-3.6.0.tgz 'mformat a:'.
You can get it from: b) Assuming that you are formatting the diskette in the first
floppy disk drive ('/dev/fd0' under Linux):
ftp://lancelot.gcs.redstone.army.mil/pub/rtems/releases/current/c/ 'mkdosfs /dev/fd0' or
After unarchiving the NEWLIB distribution (discussed earlier), the 'mkfs.msdos /dev/fd0'.
NEWLIB package must be configured for the desired host and target.
This is accomplished by changing the current directory to the top 2. To add a Linux ext2fs file system to a low-level formatted
level of the NEWLIB source tree and executing the configure script diskette, assuming that you are formatting the diskette in the
with the appropriate arguments. This step configures the NEWLIB source first floppy disk drive ('/dev/fd0' under Linux):
for the 'i386-elf32-rtems' target configuration. The libraries and
include files will be installed at <install_point>. The --verbose
option to the ./configure script is recommended so you can check how
the configuration process is progressing. Meanwhile we must do a
little patching: 'install.sh' and 'config.sub' are missing from the
'libgloss' sub-directory. A command sequence similar to the following
should be used:
cd newlib-<NEWLIB_Version> 'mke2fs /dev/fd0' or
cp configure.sub libgloss 'mkfs.ext2 /dev/fd0'.
cp install.sh libgloss
CC=gcc CFLAGS="-O4 -g" ./configure --verbose \ Next we will install using 'rawrite' or 'dd' to the 'GRUB RAW'
--target=i386-elf32-rtems \ diskette.
--prefix=<install_point>
If the configure script successfully completes, then NEWLIB may be NOTE: This will destroy any data currently on the diskette.
built. This step builds the NEWLIB package in the local directory and
does NOT install any files. The example commands specifies that gcc
should be used as the C compiler and the arguments to be used by gcc.
A command similar to the following should be used: Execute your OS's equivalent of (this should work for recent
FreeBSD versions and Linux just fine):
make CC="gcc" CFLAGS="-O4 -g" dd if=stage1 of=/dev/fd0 bs=512 count=1
dd if=stage2 of=/dev/fd0 bs=512 seek=1
If the build process successfully completes, then the NEWLIB Under DOS/Windows/NT, courtesy of Eric Hanchrow (erich@microsoft.com):
package is ready to install. A command similar to the following should
be used:
make CC="gcc" CFLAGS="-O4 -g" install * Use the copy /b command to binary concatenate the stage1 and
stage2 files together via:
If this successfully completes, then the NEWLIB package has been copy /b stage1 stage2 grub.raw
installed at <install_point>.
The documentation for the NEWLIB package is formatted using * Use rawrite.exe (which is available in many places on the net and
TeX. If TeX and some supporting tools are installed on the development in some Linux distributions) to write grub.raw to a diskette.
system, then the following command may be used to produce the
documentation in the "DVI" format:
gmake CC="gcc" CFLAGS="-O4 -g" dvi Next stage: copy the 'stage1' and 'stage2' files to the 'GRUB FS'
diskette (if you are using Linux you can mount the diskette in an
appropriate mount point and then 'cp' the files to it, if it is either
a DOS FAT or an EXT2FS diskette, or in the case of a DOS FAT diskette
you can use 'mcopy' from 'mtools'.)
If while the documentation is being formatted, the message "Cross reference values unknown; you must run TeX again." is printed, then the "DVI" files generated by this command (e.g. *.dvi in every subdirectory with documentation) must be removed and the command reexecuted. After this is done boot a PC using the 'GRUB RAW' diskette. After
this is done, you will get GRUB's command line interface. Exchange
'GRUB RAW' with the 'GRUB FS' diskette in the drive and issue the
following command from GRUB's prompt:
6. Modules install=(fd0)/stage1 (fd0) (fd0)/stage2 0x8000 (fd0)/grubmenu
----------
Modules eases the process of manipulating the environment This command will make the 'GRUB FS' diskette bootable. After this
variables required to build RTEMS. If, for whatever reason, you do not is done, you won't require the 'GRUB RAW' diskette anymore and you can
wish to use Modules, then it will be necessary to manually modify delete the 'stage1' file from the 'GRUB FS' diskette.
shell initialization files and set the required RTEMS shell variables
"manually." In this case, the Modules files are still the best place
to look for information on what variables to set and example values.
The Modules package was utilized by the RTEMS developers to make Next copy all the files you wish to load to the diskette. The GRUB
the initialization process shell independent. The Modules files used loadable test and sample files in the RTEMS distribution have '.exe'
by the RTEMS developers to configure their user environment while extension and can be found under the build point in the 'pc386/tests'
working on a particular target board are included in the directory. You can compress this files with gzip to save space if you
distribution. These require only simple modifications to be wish. GRUB loads 'gzipped' files transparently.
"localized" for the RTEMS developer. The modifications to these ASCII
files can be made with an editor such as vi or emacs.
The Modules Homepage is: Finally you have to create a GRUB menu configuration file. We will
call this file 'grubmenu'. You can call it anything as long as you use
the correct name in the 'install' command where we used 'grubmenu'.
http://www.modules.org/ The 'grubmenu' file, as far as we are interested has the following
syntax:
You can get the Modules distribution (the latest version, which title= Hello World Test
we've been using, is '3.0pre') via the homepage or directly from: kernel= (fd0)/hello.exe.gz
ftp://ftp.modules.org/pub/distrib/Modules-3.0pre.tar.gz You can add as many of this entries as you want to the 'grubmenu'
file. There should be one for each program you wish to load. The
'title=' line provides a description for the program that will appear
after boot in the GRUB menu for the user to choose and the 'kernel='
line describes where the file can be found by GRUB (you should leave
the '(fd0)/' part and just substitute the rest if you've copied the
files to the root directory of the diskette.
Just boot the PC with the 'GRUB FS' diskette and you will be able
to choose which program you want to load from GRUB's menu.
6.1. New Modules users The GRUB documentation is available in HTML format in the 'docs'
---------------------- directory of the GRUB tree starting with the 'index.html' file.
Install Modules on the development system following the
instructions in the file README in the main Modules directory. When
Modules has been installed and a user account setup to use Modules,
then proceed to the section Current Modules Users.
6.2. Current Modules users 6.3 Using NetBoot to load RTEMS PC386 applications
-------------------------- ---------------------------------------------------
If the host computer already utilizes the Modules package, then To load the '*.bt' files you can
the assistance of the system administrator responsible for the Modules
package will be required to perform the modifications described below.
The system administrator must integrate the RTEMS modules into the
existing Modules configuration. A first alternative is to copy all of
the module files provided with RTEMS into an existing modulefiles
directory. This requires that future updates of RTEMS modules will
also have to be integrated into the existing modulefiles
directory. This alternative is not recommended.
The more preferable alternative is to add the RTEMS modulefiles
directory to the MODULEPATH. This can be accomplished on an individual
user or system wide basis. For individual users, the RTEMS modules
directory can be added to the MODULEPATH of those users requiring
access to RTEMS. The default MODULEPATH is established by the Modules
initialization routine. Thus, the RTEMS modules directory must be
added to the MODULEPATH in the user's shell initialization file
(~/.profile or ~/.cshrc for example) following the Modules
initialization statement. The proper way to accomplish this is to use
the Modules use statement. For example, the following line should be
added to the user's shell initialization file:
module use <rtems_path>/modules/modulefiles
For system wide access, the RTEMS modulefiles directory can be
added to each of the shell initialization scripts in the existing
Modules package. This will require modifying the initialization of
MODULEPATH in each shell initialization file.
After integrating RTEMS modules with the existing modules, one may
proceed to the Configuring An RTEMS User section.
7. RTEMS
--------
You can get the latest free release of the C distribuition of
RTEMS (version 3.6.0), from:
ftp://lancelot.gcs.redstone.army.mil/pub/rtems/releases/current/c/
Where you'll find:
rtems-3.6.0.tgz or rtems-c_src.tgz - RTEMS sources;
rtems-3.5.1-c_doc.tgz or rtems-c_doc.tgz - RTEMS documentation;
individual_manuals/ - Sub-directory where you can get the
manuals individually.
Please note that the RTEMS documentation is slightly outdated
(most noticeably some RTEMS primitives have different protoypes) since
it refers to the previous release (3.5.1.) of RTEMS.
After unarchiving the RTEMS distribution (discussed earlier), it
is necessary to add the PC386 BSP to the source tree. This is done in
two steps.
The first step consists in unarchiving the
'rtems-3.6.0-PC386-BSP.tgz' archive over the standard rtems-3.6.0
distribution. It should be done in the same directory where
'rtems-3.6.0.tgz' was unarchived.
Next you'll need to apply the patch in
'rtems-3.6.0-PC386-BSP.diff.gz' to the RTEMS source tree. The
following command should be used:
gzip -d -c rtems-3.6.0-PC386-BSP.diff.gz | patch
also from the same directory where 'rtems-3.6.0.tgz' was unarchived.
At this stage we have RTEMS + PC386 BSP, the user environment must
be setup to build and install RTEMS.
Using this process, you'll know which files are patched and which
files are new.
7.1. Board Support Package
--------------------------
A Board Support Package (BSP) is a collection of device drivers,
initialization code, and linker scripts necessary to execute RTEMS on
a particular target board. The minimum set of device drivers for a
single processor target includes a Clock, Console I/O, and Benchmark
Timer device drivers.
The source code for the PC386 BSP can be found in the directory 'c/src/lib/libbsp/i386/pc386.
7.2. Makefile Configuration Files
---------------------------------
There are two target specific configuration files used by the
Makefile system. These configuration files specify detailed
information about the toolset, the compilation process, as well as
some general configuration information regarding the target and the
development environment. The following is a list of these
configuration files:
c/make/compilers/gcc-pc386.cfg
c/make/custom/pc386.cfg
If you're compiling to a i386+ with FPU in a standard Linux
environment, you shouldn't require any changes to these files in order
to build RTEMS (though you'll probably want to fine tune them later
on).
7.3 Creating a Customized Modules File
--------------------------------------
Files which the Modules packages may use to customize a user's
environment for building, installing, and modifying RTEMS are found in
the c/Modules/rtems directory. Each of the files in this directory
corresponds to the configuration used by the RTEMS developers for
building and installing RTEMS for a particular target board. These
files contain the Modules commands necessary to set the following
environment variables:
Variable Description
RTEMS_BSP The name of the target BSP (e.g.
mvme136 or cvme961).
RTEMS_ROOT The full path of root directory of the
RTEMS source code.
RTEMS_GNUTOOLS The full path of the root directory for
the cross-development toolset to be
used.
RTEMS_HOST The name of the operating system for
the development system.
RTEMS_LIBC_DIR The full path of the root directory for
the Standard C Library to be used.
The Modules file for the PC386 BSP is: 'c/Modules/rtems/nav-pc386'.
You MUST edit this file and set the following variables to the
correct values in your system:
- RTEMS_ROOT;
- RTEMS_GNUTOOLS (this is the directory where the links in 4.
were created);
- RTEMS_LIBC_DIR (this is the directory where the Newlib target
specific root is installed, and with reference
to 5. should be '<install_point>/i386-elf32-rtems').
7.4 Configuring an RTEMS User Using Modules
-------------------------------------------
Each user building and installing RTEMS must have their
environment configured. The user environment must have a set of
variables set in it which indicate the target BSP, host operating
system, and numerous paths.
If you'll just be using the PC386 BSP then a line of the following
type may be added to the initialization file for your shell after the
Modules initialization statement.
module load nav-pc386
Note that you must logout and login before any changes to the shell
initialization files will take effect.
If you don't wish the RTEMS environment configuration to be added
to your shell initialization file, then the "module load" statement
may be entered at the command line.
You may switch from one RTEMS configuration to another with either
of the following command sequences:
module unload <old_rtems_modulefile>
module load <new_rtems_modulefile>
OR
module switch <old_rtems_modulefile> <new_rtems_modulefile>
The command "module avail" may be used to obtain a list of the
Module files which are available to be loaded using the "module load"
command.
The command "module list" provides a list of the currently loaded
Modules.
7.5. Building RTEMS
-------------------
See the file README.configure in the top level directory for
more information.
8. RTEMS Tests
--------------
If you've completed the last step successfully, you'll find the
RTEMS sample and test files in the 'c/pc386_i386/tests' directory.
The 'sp*.bt' are the single processor tests and should all work
correctly. The same applies to the 'tm*.bt' which are the timing
tests.
The other sample ('*.bt') files should also work with the
exception of 'spfatal.bt' and 'stackchk.bt' (see 9.).
8.1 Using Diskboot or NetBoot
------------------------------
To load the '*.bt' files you can either run the 'diskboot.exe'
(which can be found in 'c/pc386_i386/build-tools') under DOS with a
command line like (this is just a quick and dirty loader - you'll have
to press return twice after entering it):
diskboot sp01.bt
Alternatively, if you have a PC connected to a network with a Alternatively, if you have a PC connected to a network with a
BOOTP server and a TFTP server (this can very well be you're Linux BOOTP server and a TFTP server (this can very well be you're Linux
RTEMS host system), you can use Gero Kuhlmann's netboot loader, to RTEMS host system), you can use Gero Kuhlmann's NetBoot loader, to
load RTEMS to a diskless PC across a network. You can get it from: load RTEMS to a diskless PC across a network. You can get it from:
ftp://sunsite.unc.edu/pub/Linux/system/boot/netboot-0.7.2.tar.gz ftp://sunsite.unc.edu/pub/Linux/system/boot/netboot-0.7.3.tar.gz
Follow the instructions contained in the package to setup the or in any of Sunsite's mirrors. It is also available from NetBoot's
homepage:
http://www.han.de/~gero/netboot
After unarchiving 'netboot-0.7.3.tar.gz' you should change to the
base directory of this and run:
./configure --disable-mknbi-dos --disable-mknbi-linux --disable-mknbi-mgl
Afterwards, you should follow the instructions contained in the
'INSTALL' file also contained in the base directory, on how to setup the
server(s) and to build a boot ROM for the client PC network card, or a server(s) and to build a boot ROM for the client PC network card, or a
boot diskette, and the client should be able to load the '*.bt' files boot diskette, and the PC client should be able to load the '*.bt' files
from the server. from the server.
For the network loader every relocation address from 0x10200 to The important sections to check in the 'INSTALL FILE' are the last two:
0x80200 are known to work correctly. For the DOS loader, relocation
addresses 0x20200, 0x40200 and 0x80200 are known to work under DOS
5.00, DOS 6.xx and DOS 7.00. You can set the relocation address in
'c/make/compilers/gcc-pc386.cfg' by setting the value of the
'RELOCADDR' variable.
8.2 Using GRUB - Setup of the server (only the BOOTP and TFTP parts - ignore NFS).
--------------- ===================
GRUB is another boot loader which may be used with pc386. It is - Setup of the client including building the bootrom
available from: ==================================================
ftp://ftp.uruk.org/public/grub/ all the rest can be safely ignored if you don't care to examine it.
http://www.uruk.org/grub/
9. Important Notes 7. Technical Information
------------------ ------------------------
The optional stack checker extension ('stackchk') doesn't seem to NOTE: All the following paths are relative to the base directory
be working properly. It reports blown task stacks even if everything of the RTEMS distribution.
seems to work properly when 'stackchk' isn't activated... This should
be properly investigated: the problem can reside with the 'PC386 BSP',
or in the interface between 'stackchk' and the BSP (maybe something
isn't being correctly initialized...). Since this doesn't seem to be a
serious BSP problem, it hasn't been dealt with, due to more prioritary
problems.
The tests which exercise the fatal error mecanisms don't work As of the writing of this HOWTO, PC386 images can be loaded either
correctly either. I've been told by Joe that 'spfatal' is outdated, and in low memory 0x10000 (64KB) until 0x97C00 (607K) using NetBoot or in
so this really isn't surprising. high memory from 0x100000 (1024KB) until the top of the available
memory using either NetBoot or GRUB.
This issues may be important and should be investigated as soon as If you want to change the default loading address from 1024KB to
possible. something else, just change the value of the variable RELOCADDR in the
'make/custom/pc386.cfg' file to the new value you want (make sure you
follow the instructions indicated before the definition of RELOCADDR).
Remember that GRUB restricts the loading addresses to values above
0x100000 (1024KB), only NetBoot can load images in low memory.
After you make any changes to RELOCADDR and if you are using
NetLoader, you'll have to recompile the
'c/src/lib/libbsp/i386/pc386/start/start16.s' file. The easiest way to
achieve this is just to 'make clean' and the 'make all' again. The
quickest way is to change to
'<build_point>/c/src/lib/libbsp/i386/pc386/start' and 'make
RTEMS_BSP=pc386 clean all'.
When programming interrupt handlers take into account that the PIC When programming interrupt handlers take into account that the PIC
is reprogrammed and so you should use the interface functions provided is reprogrammed and so you should use the interface functions provided
to garantee that everything works ok. in '<build_point>/pc386/lib/include/irq.h> to guarantee that everything
works ok.

View File

@@ -19,5 +19,5 @@
%{qrtems_debug: start_g.o%s}} %{qrtems_debug: start_g.o%s}}
*link: *link:
%{!qrtems: %(old_link)} %{qrtems: -dc -dp -N -e start} %{!qrtems: %(old_link)} %{qrtems: -dc -dp -N -e start --oformat=elf32-i386}

View File

@@ -232,6 +232,10 @@ _IBMPC_keyboard_isr(rtems_vector_number vector)
rtems_boolean rtems_boolean
_IBMPC_chrdy(char *c) _IBMPC_chrdy(char *c)
{ {
/* FIX ME!!! It doesn't work without something like the following line.
Find out why! */
printk("");
/* Check buffer our ISR builds */ /* Check buffer our ISR builds */
if (kbd_first != kbd_last) if (kbd_first != kbd_last)
{ {

View File

@@ -52,18 +52,6 @@ extern "C" {
/*-------------------------------------------------------------------------+ /*-------------------------------------------------------------------------+
| Memory related constants. | Memory related constants.
+--------------------------------------------------------------------------*/ +--------------------------------------------------------------------------*/
#ifdef RTEMS_SMALL_MEMORY /* We only have low (640K) memory. */
#define RAM_START 0x00000
#define RAM_END 0xA0000
#else /* We have at least 2048K of memory. */
#define RAM_START 0x100000
#define RAM_END 0x200000
#endif /* RTEMS_SMALL_MEMORY */
#define HEAP_SIZE 64 /* Size of libc Heap (used for malloc et al) in KBytes. */ #define HEAP_SIZE 64 /* Size of libc Heap (used for malloc et al) in KBytes. */
/*-------------------------------------------------------------------------+ /*-------------------------------------------------------------------------+

View File

@@ -8,7 +8,7 @@ VPATH = @srcdir@
RTEMS_ROOT = @top_srcdir@ RTEMS_ROOT = @top_srcdir@
PROJECT_ROOT = @PROJECT_ROOT@ PROJECT_ROOT = @PROJECT_ROOT@
PGMS=${ARCH}/start.o PGMS=${ARCH}/start.o ${ARCH}/start16.bin
# C source names, if any, go here -- minus the .c # C source names, if any, go here -- minus the .c
C_PIECES= C_PIECES=
@@ -18,7 +18,7 @@ C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
H_FILES= H_FILES=
# Assembly source names, if any, go here -- minus the .s # Assembly source names, if any, go here -- minus the .s
S_PIECES=start S_PIECES=start16 start
S_FILES=$(S_PIECES:%=%.s) S_FILES=$(S_PIECES:%=%.s)
S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o) S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
@@ -50,8 +50,21 @@ LDFLAGS +=
CLEAN_ADDITIONS += CLEAN_ADDITIONS +=
CLOBBER_ADDITIONS += CLOBBER_ADDITIONS +=
all: ${ARCH} $(SRCS) $(OBJS) $(PGM) all: ${ARCH} $(SRCS) $(OBJS) $(PGMS)
$(INSTALL_VARIANT) -m 555 ${PGMS} ${PROJECT_RELEASE}/lib $(INSTALL_VARIANT) -m 555 ${PGMS} ${PROJECT_RELEASE}/lib
# Install the program(s), appending _g or _p as appropriate. # Install the program(s), appending _g or _p as appropriate.
# for include files, just use $(INSTALL) # for include files, just use $(INSTALL)
LINKCMDS=$(srcdir)/../startup/linkcmds
${ARCH}/start16.o: start16.s
sed -e 's/\/\/.*$$//' < $< | $(CPP) $(ASMFLAGS) -I. -I$(srcdir) \
-DASM -DSTART32ADDR=$(RELOCADDR) - > $*.i
$(AS) $(ASFLAGS) -o $@ $*.i
${ARCH}/start16.bin: ${ARCH}/start16.o
$(LD) -N -T $(LINKCMDS) -Ttext $(START16ADDR) -e start16 -nostdlib \
--oformat=elf32-i386 -o $(basename $@).obj $(basename $@).o
$(OBJCOPY) -O binary $(basename $@).obj $@

View File

@@ -30,26 +30,12 @@
| * http://www.OARcorp.com/rtems/license.html. | * http://www.OARcorp.com/rtems/license.html.
| ************************************************************************** | **************************************************************************
| |
| Also based on (from the Linux source tree):
| video.S - Copyright (C) 1995, 1996 Martin Mares <mj@k332.feld.cvut.cz>
|
| $Id$ | $Id$
+--------------------------------------------------------------------------*/ +--------------------------------------------------------------------------*/
#include "asm.h" #include "asm.h"
/*----------------------------------------------------------------------------+
| Constants
+----------------------------------------------------------------------------*/
#ifdef pc386
.set PROT_CODE_SEG, 0x08 # offset of code segment descriptor into GDT
.set CR0_PE, 1 # protected mode flag on CR0 register
#endif /* pc386 */
/*----------------------------------------------------------------------------+ /*----------------------------------------------------------------------------+
| A Descriptor table register has the following format: | A Descriptor table register has the following format:
+----------------------------------------------------------------------------*/ +----------------------------------------------------------------------------*/
@@ -58,6 +44,13 @@
.set DTR_BASE, 2 # offset of four byte base address .set DTR_BASE, 2 # offset of four byte base address
.set DTR_SIZE, 6 # size of DTR register .set DTR_SIZE, 6 # size of DTR register
/*----------------------------------------------------------------------------+
| Size of heap and stack:
+----------------------------------------------------------------------------*/
.set HEAP_SIZE, 0x2000
.set STACK_SIZE, 0x1000
/*----------------------------------------------------------------------------+ /*----------------------------------------------------------------------------+
| CODE section | CODE section
+----------------------------------------------------------------------------*/ +----------------------------------------------------------------------------*/
@@ -72,65 +65,9 @@ BEGIN_CODE
SYM (start): SYM (start):
/*----------------------------------------------------------------------------+
| Switch VGA video to 80 lines x 50 columns mode. Has to be done before turning
| protected mode on since it uses BIOS int 10h (video) services.
+----------------------------------------------------------------------------*/
#if defined(pc386) && defined(RTEMS_VIDEO_80x50)
.code16
movw $0x0003, ax # forced set
int $0x10
movw $0x1112, ax # use 8x8 font
xorb %bl, %bl
int $0x10
movw $0x1201, ax # turn off cursor emulation
movb $0x34, %bl
int $0x10
movb $0x01, ah # define cursor (scan lines 0 to 7)
movw $0x0007, cx
int $0x10
.code32
#endif /* pc386 && RTEMS_VIDEO_80x50 */
nop nop
cli # DISABLE INTERRUPTS!!! cli # DISABLE INTERRUPTS!!!
/*----------------------------------------------------------------------------+
| Bare PC machines boot in real mode! We have to turn protected mode on.
+----------------------------------------------------------------------------*/
#ifdef pc386
data16
movl $ SYM(gdtptr), eax
data16
andl $0x0000ffff, eax # get offset into segment
addr16
lgdt cs:(eax) # load Global Descriptor Table
data16
movl $ SYM(idtptr), eax
data16
andl $0x0000ffff, eax # get offset into segment
addr16
lidt cs:(eax) # load Interrupt Descriptor Table
movl %cr0, eax
data16
orl $CR0_PE, eax
movl eax, %cr0 # turn on protected mode
data16
ljmp $PROT_CODE_SEG, $ SYM(next) # flush prefetch queue
SYM(next):
#endif /* pc386 */
/*----------------------------------------------------------------------------+ /*----------------------------------------------------------------------------+
| Load the segment registers (this is done by the board's BSP) and perform any | Load the segment registers (this is done by the board's BSP) and perform any
| other board specific initialization procedures. | other board specific initialization procedures.
@@ -149,9 +86,9 @@ SYM(next):
SYM (_establish_stack): SYM (_establish_stack):
movl $_end, eax # eax = end of bss/start of heap movl $_end, eax # eax = end of bss/start of heap
addl $heap_size, eax # eax = end of heap addl $HEAP_SIZE, eax # eax = end of heap
movl eax, stack_start # Save for brk() routine movl eax, stack_start # Save for brk() routine
addl $stack_size, eax # make room for stack addl $STACK_SIZE, eax # make room for stack
andl $0xffffffc0, eax # align it on 16 byte boundary andl $0xffffffc0, eax # align it on 16 byte boundary
movl eax, esp # set stack pointer movl eax, esp # set stack pointer
movl eax, ebp # set base pointer movl eax, ebp # set base pointer
@@ -262,6 +199,7 @@ SYM (no_gdt_load):
cmpb $0, SYM (_Do_Load_IDT) # Should the new IDT be loaded? cmpb $0, SYM (_Do_Load_IDT) # Should the new IDT be loaded?
je SYM (no_idt_load) # NO, then branch je SYM (no_idt_load) # NO, then branch
lidt SYM (_New_IDTR) # load the new IDT lidt SYM (_New_IDTR) # load the new IDT
SYM (no_idt_load): SYM (no_idt_load):
/*---------------------------------------------------------------------+ /*---------------------------------------------------------------------+
@@ -315,41 +253,6 @@ END_CODE
BEGIN_DATA BEGIN_DATA
#ifdef pc386
/**************************
* GLOBAL DESCRIPTOR TABLE *
**************************/
.align 4
SYM(gdtptr):
/* we use the NULL descriptor to store the GDT pointer - a trick quite
nifty due to: Robert Collins (rcollins@x86.org) */
.word gdtlen - 1
.long gdtptr
.word 0x0000
/* code segment */
.word 0xffff, 0
.byte 0, 0x9f, 0xcf, 0
/* data segment */
.word 0xffff, 0
.byte 0, 0x93, 0xcf, 0
.set gdtlen, . - gdtptr # length of GDT
/*************************************
* INTERRUPT DESCRIPTOR TABLE POINTER *
*************************************/
.align 4
SYM(idtptr):
.word 0x07ff # limit at maximum (allows all 256 interrupts)
.word 0, 0 # base at 0
#endif /* pc386 */
EXTERN (Do_Load_IDT) # defined in the BSP EXTERN (Do_Load_IDT) # defined in the BSP
EXTERN (Do_Load_GDT) # defined in the BSP EXTERN (Do_Load_GDT) # defined in the BSP
@@ -370,11 +273,13 @@ END_DATA
BEGIN_BSS BEGIN_BSS
PUBLIC (heap_size) PUBLIC (_heap_size)
.set heap_size, 0x2000 SYM (_heap_size):
.long HEAP_SIZE
PUBLIC (stack_size) PUBLIC (_stack_size)
.set stack_size, 0x1000 SYM (_stack_size):
.long STACK_SIZE
PUBLIC (Interrupt_descriptor_table) PUBLIC (Interrupt_descriptor_table)
SYM (Interrupt_descriptor_table): SYM (Interrupt_descriptor_table):
@@ -390,14 +295,8 @@ SYM (_New_IDTR):
PUBLIC (_Global_descriptor_table) PUBLIC (_Global_descriptor_table)
SYM (_Global_descriptor_table): SYM (_Global_descriptor_table):
#ifdef pc386
.space (3 * 8) # the PC386 bsp only needs 3 segment descriptors: .space (3 * 8) # the PC386 bsp only needs 3 segment descriptors:
#else # NULL, CODE and DATA # NULL, CODE and DATA
.space (8192 * 8)
#endif /* pc386 */
PUBLIC (_Original_GDTR) PUBLIC (_Original_GDTR)
SYM (_Original_GDTR): SYM (_Original_GDTR):
.space DTR_SIZE .space DTR_SIZE

View File

@@ -41,16 +41,13 @@
/*-------------------------------------------------------------------------+ /*-------------------------------------------------------------------------+
| Global Variables | Global Variables
+--------------------------------------------------------------------------*/ +--------------------------------------------------------------------------*/
#ifdef RTEMS_SMALL_MEMORY
extern rtems_unsigned32 _end; /* End of BSS. Defined in 'linkcmds'. */ extern rtems_unsigned32 _end; /* End of BSS. Defined in 'linkcmds'. */
extern rtems_unsigned32 _heap_size; /* Size of stack. Defined in 'start.s'. */
extern rtems_unsigned32 _stack_size; /* Size of heap. Defined in 'start.s'. */
rtems_unsigned32 rtemsFreeMemStart = (rtems_unsigned32)&_end; rtems_unsigned32 rtemsFreeMemStart;
/* Address of start of free memory - should be updated /* Address of start of free memory - should be updated
after creating new partitions or regions. */ after creating new partitions or regions. */
#else
rtems_unsigned32 rtemsFreeMemStart = RAM_START;
/* RAM_START defined in 'bsp.h'. */
#endif /* RTEMS_SMALL_MEMORY */
/* The original BSP configuration table from the application and our copy of it /* The original BSP configuration table from the application and our copy of it
with some changes. */ with some changes. */
@@ -105,6 +102,9 @@ void bsp_pretasking_hook(void)
+--------------------------------------------------------------------------*/ +--------------------------------------------------------------------------*/
void bsp_start( void ) void bsp_start( void )
{ {
rtemsFreeMemStart = (rtems_unsigned32)&_end + _heap_size + _stack_size;
/* set the value of start of free memory. */
/* If we don't have command line arguments set default program name. */ /* If we don't have command line arguments set default program name. */
Cpu_table.pretasking_hook = bsp_pretasking_hook; /* init libc, etc. */ Cpu_table.pretasking_hook = bsp_pretasking_hook; /* init libc, etc. */
@@ -118,8 +118,11 @@ void bsp_start( void )
Cpu_table.interrupt_stack_size = 4096; Cpu_table.interrupt_stack_size = 4096;
Cpu_table.extra_mpci_receive_server_stack = 0; Cpu_table.extra_mpci_receive_server_stack = 0;
/* Place RTEMS workspace at top of physical RAM (RAM_END defined in 'bsp.h' */ /* Place RTEMS workspace at beginning of free memory. */
BSP_Configuration.work_space_start = if (rtemsFreeMemStart & (CPU_ALIGNMENT - 1)) /* not aligned => align it */
(void *)(RAM_END - BSP_Configuration.work_space_size); rtemsFreeMemStart = (rtemsFreeMemStart+CPU_ALIGNMENT) & ~(CPU_ALIGNMENT-1);
BSP_Configuration.work_space_start = (void *)rtemsFreeMemStart;
rtemsFreeMemStart += BSP_Configuration.work_space_size;
} /* bsp_start */ } /* bsp_start */

View File

@@ -68,27 +68,6 @@ BEGIN_CODE
EXTERN (establish_stack) EXTERN (establish_stack)
/*----------------------------------------------------------------------------+
| empty_8042
+------------------------------------------------------------------------------
| This routine checks that the keyboard command queue is empty (after emptying
| the output buffers).
| No timeout is used - if this hangs there is something wrong with the machine,
| and we probably couldn't proceed anyway.
+----------------------------------------------------------------------------*/
SYM(empty_8042):
call delay
inb $0x64, al # 8042 status port
testb $0x01, al # output buffer?
jz SYM(no_output)
call SYM(delay)
in $0x60, al # read it
jmp SYM(empty_8042)
SYM(no_output):
test $0x02, al # is input buffer full?
jnz SYM(empty_8042) # yes - loop
ret
/*----------------------------------------------------------------------------+ /*----------------------------------------------------------------------------+
| delay | delay
+------------------------------------------------------------------------------ +------------------------------------------------------------------------------
@@ -100,8 +79,8 @@ SYM(delay):
/*-------------------------------------------------------------------------+ /*-------------------------------------------------------------------------+
| Function: _load_segments | Function: _load_segments
| Description: Load board segment registers with apropriate values + enable | Description: Load board segment registers with apropriate values +
A20 line + reprogram PIC. | reprogram PIC.
| Global Variables: None. | Global Variables: None.
| Arguments: None. | Arguments: None.
| Returns: Nothing. | Returns: Nothing.
@@ -115,18 +94,6 @@ SYM (_load_segments):
LOAD_SEGMENTS(RESET_FS, fs) LOAD_SEGMENTS(RESET_FS, fs)
LOAD_SEGMENTS(RESET_GS, gs) LOAD_SEGMENTS(RESET_GS, gs)
/*---------------------------------------------------------------------+
| we have to enable A20 in order to access memory above 1MByte
+---------------------------------------------------------------------*/
call SYM(empty_8042)
movb $0xD1, al # command write
outb al, $0x64
call SYM(empty_8042)
movb $0xDF, al # A20 on
outb al, $0x60
call SYM(empty_8042)
/*---------------------------------------------------------------------+ /*---------------------------------------------------------------------+
| Now we have to reprogram the interrupts :-(. We put them right after | Now we have to reprogram the interrupts :-(. We put them right after
| the intel-reserved hardware interrupts, at int 0x20-0x2F. There they | the intel-reserved hardware interrupts, at int 0x20-0x2F. There they

View File

@@ -22,11 +22,14 @@ VPATH=@srcdir@
USE_HOST_COMPILER=yes USE_HOST_COMPILER=yes
# C source names, if any, go here -- minus the .c # C source names, if any, go here -- minus the .c
C_PIECES=bin2boot C_PIECES=
CC_PIECES=bin2boot Header Image
C_FILES=$(C_PIECES:%=%.c) C_FILES=$(C_PIECES:%=%.c)
CC_FILES=$(CC_PIECES:%=%.cc)
C_O_FILES=$(C_PIECES:%=$(ARCH)/%.o) C_O_FILES=$(C_PIECES:%=$(ARCH)/%.o)
CC_O_FILES=$(CC_PIECES:%=$(ARCH)/%.o)
H_FILES= H_FILES=bytetype.h Header.h Image.h
SRCS=$(C_FILES) $(CC_FILES) $(H_FILES) SRCS=$(C_FILES) $(CC_FILES) $(H_FILES)
OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES) OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
@@ -43,10 +46,11 @@ include $(RTEMS_ROOT)/make/leaf.cfg
DEFINES += DEFINES +=
CPPFLAGS += CPPFLAGS +=
CFLAGS += CFLAGS +=
CXXFLAGS += -g -Wall
LD_PATHS += LD_PATHS +=
LD_LIBS += LD_LIBS += -lstdc++
LDFLAGS += LDFLAGS += -g
# #
# Add your list of files to delete here. The config files # Add your list of files to delete here. The config files
@@ -60,5 +64,10 @@ CLOBBER_ADDITIONS +=
all: $(ARCH) $(SRCS) $(PGMS) all: $(ARCH) $(SRCS) $(PGMS)
$(INSTALL) -m 555 $(PGMS) ${PROJECT_RELEASE}/build-tools $(INSTALL) -m 555 $(PGMS) ${PROJECT_RELEASE}/build-tools
uudecode < $(srcdir)/diskboot.uue \
> $(PROJECT_RELEASE)/build-tools/diskboot.exe $(ARCH)/bin2boot: $(OBJS)
$(CC) $(LDFLAGS) $^ -o $@ $(LD_LIBS)
$(ARCH)/bin2boot.o : bin2boot.cc Header.h Image.h bytetype.h
$(ARCH)/Header.o: Header.cc Header.h bytetype.h
$(ARCH)/Image.o: Image.cc Image.h bytetype.h

View File

@@ -1,241 +0,0 @@
/*-------------------------------------------------------------------------+
| bin2boot.c v1.1 - PC386 BSP - 1997/08/18
+--------------------------------------------------------------------------+
| This file contains the i386 binary to boot image filter.
+--------------------------------------------------------------------------+
| (C) Copyright 1997 -
| - NavIST Group - Real-Time Distributed Systems and Industrial Automation
|
| http://pandora.ist.utl.pt
|
| Instituto Superior Tecnico * Lisboa * PORTUGAL
+--------------------------------------------------------------------------+
| Disclaimer:
|
| This file is provided "AS IS" without warranty of any kind, either
| expressed or implied.
|
| $Id$
+--------------------------------------------------------------------------*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "bytetype.h"
#include "bootimg.h"
/*-------------------------------------------------------------------------+
| Constants
+--------------------------------------------------------------------------*/
#define SEG_MASK 0xffff0000
/* Mask for segment part of seg:off address. */
#define OFF_MASK 0x0000ffff
/* Mask for offset part of seg:off address. */
#define DEFAULT_START_ADDR 0x10200 /* Default start address for binary. */
#define BOOTIMG_HDR_SIZE 0x0200 /* Size of output file header. */
#define BUFFER_BLOCK_SIZE 0x1000 /* Size of transfer buffer size. */
#define LAST_BLOCK_SIZE 0x0200
/* The output file must have a size multiple of this value. */
/*-------------------------------------------------------------------------+
| Macros
+--------------------------------------------------------------------------*/
#define getSeg(x) (Word)((x) >> 16)
/* Return seg part (Word) of a seg:off address (DWord). */
#define getOff(x) (Word)((x) & OFF_MASK)
/* Return off part (Word) of a seg:off address (DWord). */
#define getSegOff(x) ((((x) & SEG_MASK) << 12) + ((x) & OFF_MASK))
/* Converts a flat address to a seg:off address. */
/*-------------------------------------------------------------------------+
| Global Variables
+--------------------------------------------------------------------------*/
const char UsageMsg[] = "\
Usage: bin2boot [<infile> [<outfile>]] [-s <start_address>] [-v]\n\
\n\
<infile> : input file name\n\
<outfile> : output file name\n\
-s <outfile> : start address of binary image\n\
-m <size> : actual size (for compressed images)\n\
-v : verbose output\n"; /* Usage message. */
/*-------------------------------------------------------------------------+
| External Prototypes (for use with getopt)
+--------------------------------------------------------------------------*/
extern char *optarg;
int getopt(int, char *const[], const char *);
/*-------------------------------------------------------------------------+
| Auxiliary Functions
+--------------------------------------------------------------------------*/
static DWord
getNumArg(char *arg)
{
char *dummy;
if (arg[0] == '0')
if ((arg[1] == 'x') || (arg[1] == 'X')) /* Hexadecimal */
return (DWord)strtol(arg, &dummy, 16);
else /* Octal */
return (DWord)strtol(arg, &dummy, 8);
else /* Decimal */
return (DWord)strtol(arg, &dummy, 10);
} /* getNumArg */
/*-------------------------------------------------------------------------+
| Main
+--------------------------------------------------------------------------*/
void main(int argc, char *argv[])
{
FileHeader bootimgFileHdr; /* Output file header. */
LoadingInfo imageInfo; /* Section header. */
Byte auxBuf[BUFFER_BLOCK_SIZE]; /* */
DWord nRead; /* Number of bytes read. */
Word padSize; /* Size of padding at end of file. */
char *progName = argv[0]; /* Program name for errors. */
FILE *fpIn = stdin;
FILE *fpOut = stdout;
DWord binStart = DEFAULT_START_ADDR; /* Start address of image. */
DWord memLen = 0; /* Real length for compressed images. */
char currArg;
int argCount;
int flag; /* general purpose flag */
int verbose = 0; /* flag for verbose output */
while ((currArg = getopt(argc, argv, "hm:s:v")) >= 0) /* parse command line */
switch (currArg)
{
case 'h' :
fprintf(stderr, UsageMsg);
exit(0);
break;
case 'm' :
memLen = getNumArg(optarg);
break;
case 's' :
binStart = getNumArg(optarg);
break;
case 'v' :
verbose = 1;
break;
default :
fprintf(stderr, UsageMsg);
exit(1);
break;
} /* switch */
flag = 0;
for (argCount = 1; argCount < argc; argCount++)
if (argv[argCount][0] == '-')
{
if (argv[argCount][1] == 's')
argCount++;
}
else if (flag) /* we already have the input file => output file */
{
if ((fpOut = fopen(argv[argCount], "w")) == NULL)
{
fprintf(stderr, "%s: can't open %s\n", progName, argv[argCount]);
exit(1);
}
}
else /* input file */
{
if ((fpIn = fopen(argv[argCount], "r")) == NULL)
{
fprintf(stderr, "%s: can't open %s\n", progName, argv[argCount]);
exit(1);
}
flag = 1;
}
/*** begin: Conversion to Bootimg */
/*** File Header */
if (verbose)
fprintf(stderr, "\nBoot Image File Header:\n\n");
bootimgFileHdr.magicNum = BOOT_IMAGE_MAGIC; /* 4 bytes - magic number */
bootimgFileHdr.flagsLen = NON_VENDOR_LEN; /* 4 bytes - flags and length */
bootimgFileHdr.locAddr = getSegOff(binStart - BOOTIMG_HDR_SIZE);
/* 4 bytes - location address in ds:bx format */
bootimgFileHdr.execAddr = getSegOff(binStart);
/* 4 bytes - execute address in cs:ip format */
if (verbose)
{
fprintf(stderr, ">> location address in ds:bx format: %04x:%04x\n",
getSeg(bootimgFileHdr.locAddr), getOff(bootimgFileHdr.locAddr));
fprintf(stderr, ">> execute address in cs:ip format: %04x:%04x\n",
getSeg(bootimgFileHdr.execAddr), getOff(bootimgFileHdr.execAddr));
}
/*** Write File Header to output file */
fwrite((void *)(& bootimgFileHdr), sizeof(FileHeader), 1, fpOut);
/*** Sections */
if (verbose)
fprintf(stderr, "\nCode Section:\n\n");
imageInfo.flagsTagsLens = 0x04000004;
/* flags, vendor's tags, vendor and non-vendor lengths */
imageInfo.loadAddr = binStart; /* load address */
rewind(fpIn);
fseek(fpIn, 0, SEEK_END);
nRead = ftell(fpIn);
rewind(fpIn);
padSize = LAST_BLOCK_SIZE - (nRead % LAST_BLOCK_SIZE);
imageInfo.imageLength = nRead + padSize; /* image length */
imageInfo.memoryLength = (memLen != 0) ? memLen : imageInfo.imageLength;
/* memory length */
fwrite((void *)(&imageInfo), sizeof(LoadingInfo), 1, fpOut);
if (verbose)
{
fprintf(stderr, ">> load address: 0x%08lx\n", imageInfo.loadAddr);
fprintf(stderr, ">> image length: 0x%08lx\n", imageInfo.imageLength);
fprintf(stderr, ">> memory length: 0x%08lx\n\n", imageInfo.memoryLength);
}
nRead = BOOTIMG_HDR_SIZE - sizeof(FileHeader) - sizeof(LoadingInfo);
memset((void *)auxBuf, 0x00, nRead);
fwrite((void *)auxBuf, 1, nRead, fpOut);
nRead = fread((void *)auxBuf, 1, BUFFER_BLOCK_SIZE, fpIn);
while (!feof(fpIn))
{
fwrite((void *)auxBuf, BUFFER_BLOCK_SIZE, 1, fpOut);
nRead = fread((void *)auxBuf, 1, BUFFER_BLOCK_SIZE, fpIn);
}
fwrite((void *)auxBuf, 1, nRead, fpOut);
memset((void *)auxBuf, 0x00, padSize);
fwrite((void *)auxBuf, 1, padSize, fpOut);
fclose(fpOut);
fclose(fpIn);
/*** end: Conversion to Bootimg */
exit(0);
} /* main */

View File

@@ -46,4 +46,6 @@ $(LIB): ${OBJS}
all: ${ARCH} $(SRCS) $(LIB) all: ${ARCH} $(SRCS) $(LIB)
$(INSTALL_VARIANT) -m 644 $(LIB) ${PROJECT_RELEASE}/lib $(INSTALL_VARIANT) -m 644 $(LIB) ${PROJECT_RELEASE}/lib
# we create here a directory specific to the PC386 BSP to store the BootImage
# files so they can be easily found
mkdir -p ${PROJECT_RELEASE}/BootImgs

View File

@@ -42,7 +42,7 @@ HAS_KA9Q=no
define make-target-options define make-target-options
@echo "/* #define NDEBUG 1 */ " >>$@ @echo "/* #define NDEBUG 1 */ " >>$@
@echo "#define RTEMS_TEST_NO_PAUSE 1" >>$@ @echo "/* #define RTEMS_TEST_NO_PAUSE 1 */" >>$@
@echo "/* #define RTEMS_DEBUG 1 */" >>$@ @echo "/* #define RTEMS_DEBUG 1 */" >>$@
endef endef
@@ -51,13 +51,19 @@ endef
# Usage ref: src/tests/sptest/sp1/Makefile # Usage ref: src/tests/sptest/sp1/Makefile
#+--------------------------------------------------------------------------+ #+--------------------------------------------------------------------------+
#| Relocation address. Set this to the linear address where you want your code #| Set the value of RELOCADDR to the address where you want your image to
#| to start. It should abide to the following constraints: #| load. If you'll be using GRUB to load the images it will have to be >=
#| RELOCADDR >= 0x10200 #| 0x100000 (1024K). If you are using NetBoot to load the images it can be
#| RELOCADDR + 'image file size' < 0xA0000 #| >= 0x10000 (64K) AND <= 0x97C00 (607K) OR >= 0x100000 (1024K). The memory
#| RELOCADDR % 4 = 0 (i.e. aligned on a 4 byte boundary) #| top is of course another limit. Make sure there is enough space before the
#| upper memory limits for the image and the memory allocated by it to fit.
#| Make sure the value you choose is aligned to 4 bytes.
#+--------------------------------------------------------------------------+ #+--------------------------------------------------------------------------+
RELOCADDR=0x00020200 RELOCADDR=0x00100000
START16FILE=$(PROJECT_RELEASE)/lib/start16.bin
START16ADDR=0x00097C00
HEADERADDR=0x00097E00
# The following are definitions of make-exe which will work using ld as # The following are definitions of make-exe which will work using ld as
# is currently required. It is expected that as of gcc 2.8, the end user # is currently required. It is expected that as of gcc 2.8, the end user
@@ -66,20 +72,28 @@ RELOCADDR=0x00020200
ifeq ($(RTEMS_USE_GCC272),yes) ifeq ($(RTEMS_USE_GCC272),yes)
define make-exe define make-exe
$(LD) -N -T $(LINKCMDS) -Ttext $(RELOCADDR) -e start -nostdlib \ $(LD) -N -T $(LINKCMDS) -Ttext $(RELOCADDR) -e start -nostdlib \
-o $(basename $@).elf \ -o $(basename $@).obj \
$(START_FILE) $(LINK_OBJS) --start-group $(LINK_LIBS) --end-group $(START_FILE) $(LINK_OBJS) --start-group $(LINK_LIBS) --end-group
$(OBJCOPY) -O binary --set-start $(RELOCADDR) $(basename $@).elf $@ $(OBJCOPY) -O a.out-i386 --remove-section=.rodata --strip-unneeded \
$(PROJECT_TOOLS)/bin2boot -v $@ $(basename $@).bin -s $(RELOCADDR) $(basename $@).obj $@
$(NM) -g -n $(basename $@).elf > $(basename $@).num $(OBJCOPY) -O binary $(basename $@).obj $(basename $@).bin
$(SIZE) $(basename $@).elf $(PROJECT_TOOLS)/bin2boot -v $(basename $@).bin $(HEADERADDR)\
$(START16FILE) $(START16ADDR) 0 $(basename $@).bin $(RELOCADDR) 0
$(NM) -g -n $(basename $@).obj > $(basename $@).num
$(SIZE) $(basename $@).obj
$(INSTALL_VARIANT) -m 555 $(basename $@).bt ${PROJECT_RELEASE}/BootImgs
endef endef
else else
define make-exe define make-exe
$(CC) $(CFLAGS) $(CFLAGS_LD) -o $(basename $@).elf $(LINK_OBJS) $(CC) $(CFLAGS) $(CFLAGS_LD) -Ttext $(RELOCADDR) -o $(basename $@).obj $(LINK_OBJS)
$(OBJCOPY) -O binary --set-start $(RELOCADDR) $(basename $@).elf $@ $(OBJCOPY) -O a.out-i386 --remove-section=.rodata --strip-unneeded \
$(PROJECT_TOOLS)/bin2boot -v $@ $(basename $@).bin -s $(RELOCADDR) $(basename $@).obj $@
$(NM) -g -n $(basename $@).elf > $(basename $@).num $(OBJCOPY) -O binary $(basename $@).obj $(basename $@).bin
$(SIZE) $(basename $@).elf $(PROJECT_TOOLS)/bin2boot -v $(basename $@).bt $(HEADERADDR)\
$(START16FILE) $(START16ADDR) 0 $(basename $@).bin $(RELOCADDR) 0
$(NM) -g -n $(basename $@).obj > $(basename $@).num
$(SIZE) $(basename $@).obj
$(INSTALL_VARIANT) -m 555 $(basename $@).bt ${PROJECT_RELEASE}/BootImgs
endef endef
endif endif