Index: c/src/lib/libbsp/i386/pc386/HOWTO
===================================================================
--- c/src/lib/libbsp/i386/pc386/HOWTO	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/HOWTO	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,496 @@
+#
+#  $Id$
+#
+
+Joel's Note:
+
+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
+---------------
+
+    This howto tries to explain how to setup the RTEMS host
+environment on a Linux based PC so that RTEMS applications can be
+built for and run in a bare PC 386+.
+
+    Please note that everything in the following text using the
+notation '<...>' is just an alias to something and should always be
+substituted by the real thing!
+
+2. Unarchiving
+--------------
+
+    Files which have been "tarred, zipped" (i.e. .tar.gz or .tgz
+extension) may be unarchived with a command similar to one of the
+following:
+
+      gzcat <file>.tgz | tar xvof -
+
+    OR
+
+      gunzip -c <file>.tgz | tar xvof -
+
+    OR
+
+      gtar xzvf <file>.tgz
+
+    NOTE: gunzip -c is equivalent to gzcat, while gtar is GNU tar.
+
+    Given that the necessary utility programs are installed, any of
+the above commands will extract the contents of <file>.tar.gz into the
+current directory. All of the RTEMS components will be extracted into
+the subdirectory rtems-3.2.0. To view the contents of a component
+without restoring any files, use a command similar to the following:
+
+      gzcat <file>.tgz | tar tvf -
+
+3. The building tools (gcc, binutils, et al.)
+---------------------------------------------
+
+    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
+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
+still don't have a 'binary' target in 'objcopy'. We need objcopy's
+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 +
+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
+Linux and sources from:
+
+    ftp://sunsite.unc.edu/pub/Linux/GCC/
+
+      binutils-2.8.1.0.1.bin.tar.gz
+      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.
+
+4. Creating aliases for gcc and the binutils
+--------------------------------------------
+
+    The NEWLIB expects to be compiled by a cross-compiler. The easiest
+(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
+quickly. It assumes that the native Linux 'gcc' and 'binutils' reside
+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 ---
+
+#!sh
+ln -sf /usr/bin/ar i386-elf32-rtems-ar
+ln -sf /usr/bin/as i386-elf32-rtems-as
+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 ---
+ 
+5. Building Newlib
+------------------
+
+    The next step is to build and install the NEWLIB package. The
+version we've been using and have tested is:
+
+      newlib-1.7.0-posix-rtems-3.6.0.tgz
+
+    You can get it from:
+
+      ftp://lancelot.gcs.redstone.army.mil/pub/rtems/releases/current/c/
+
+    After unarchiving the NEWLIB distribution (discussed earlier), the
+NEWLIB package must be configured for the desired host and target.
+
+    This is accomplished by changing the current directory to the top
+level of the NEWLIB source tree and executing the configure script
+with the appropriate arguments. This step configures the NEWLIB source
+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>
+
+      cp configure.sub libgloss
+      cp install.sh libgloss
+
+      CC=gcc CFLAGS="-O4 -g" ./configure --verbose \
+             --target=i386-elf32-rtems \
+             --prefix=<install_point>
+
+    If the configure script successfully completes, then NEWLIB may be
+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:
+
+      make CC="gcc" CFLAGS="-O4 -g"
+
+    If the build process successfully completes, then the NEWLIB
+package is ready to install. A command similar to the following should
+be used:
+
+      make CC="gcc" CFLAGS="-O4 -g" install
+
+    If this successfully completes, then the NEWLIB package has been
+installed at <install_point>.
+
+    The documentation for the NEWLIB package is formatted using
+TeX. If TeX and some supporting tools are installed on the development
+system, then the following command may be used to produce the
+documentation in the "DVI" format:
+
+      gmake CC="gcc" CFLAGS="-O4 -g" dvi
+
+    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.
+
+6. Modules
+----------
+
+    Modules eases the process of manipulating the environment
+variables required to build RTEMS. If, for whatever reason, you do not
+wish to use Modules, then it will be necessary to manually modify
+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
+the initialization process shell independent. The Modules files used
+by the RTEMS developers to configure their user environment while
+working on a particular target board are included in the
+distribution. These require only simple modifications to be
+"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:
+
+      http://www.modules.org/
+
+    You can get the Modules distribution (the latest version, which
+we've been using, is '3.0pre') via the homepage or directly from:
+
+      ftp://ftp.modules.org/pub/distrib/Modules-3.0pre.tar.gz
+
+
+    6.1. New Modules users
+    ----------------------
+
+    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
+    --------------------------
+
+    If the host computer already utilizes the Modules package, then
+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
+    -------------------
+
+    By default, the PC386 RTEMS BSP is installed into the directory
+'c/pc386_i386'. If this is not the desired installation point, then
+modify the following line in the file 'c/make/custom/pc386.cfg':
+
+      PROJECT_HOME=$(PROJECT_ROOT)/$(RTEMS_BSP)
+
+    Once the root directory of the install point has been set, the
+following steps are required to build and install RTEMS (NOTE: If the
+Modules files are used, the environment variable '$r' is set to point
+to the top directory for the RTEMS implementation selected in the
+current environment. This is the directory 'c' in the RTEMS
+distribution.):
+
+      cd $r
+      make install
+
+    If this completes successfully, then RTEMS has been built and
+installed.
+
+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.).
+
+    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
+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
+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
+
+    Follow the instructions contained in the package to setup the
+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
+from the server.
+
+    For the network loader every relocation address from 0x10200 to
+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.
+ 
+9. Important Notes
+------------------
+
+    The optional stack checker extension ('stackchk') doesn't seem to
+be working properly. It reports blown task stacks even if everything
+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
+correctly either. I've been told by Joe that 'spfatal' is outdated, and
+so this really isn't surprising.
+
+    This issues may be important and should be investigated as soon as
+possible.
+
+    When programming interrupt handlers take into account that the PIC
+is reprogrammed and so you should use the interface functions provided
+to garantee that everything works ok.
Index: c/src/lib/libbsp/i386/pc386/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,15 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/directory.cfg
+
+# wrapup is the one that actually builds and installs the library
+#  from the individual .rel files built in other directories
+SUB_DIRS=include tools start startup clock console timer wrapup
Index: c/src/lib/libbsp/i386/pc386/bsp_specs
===================================================================
--- c/src/lib/libbsp/i386/pc386/bsp_specs	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/bsp_specs	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,18 @@
+%rename cpp old_cpp
+%rename lib old_lib
+%rename endfile old_endfile
+%rename startfile old_startfile
+%rename link old_link
+
+*cpp:
+%(old_cpp) %{qrtems: -D__embedded__} -Asystem(embedded)
+
+*lib:
+%{!qrtems: %(old_lib)} %{qrtems: --start-group -lrtemsall -lc -lgcc --end-group}
+
+*startfile:
+%{!qrtems: %(old_startfile)} %{qrtems: start.o%s}
+
+*link:
+%{!qrtems: %(old_link)} %{qrtems: -dc -dp -N -T linkcmds%s -e start}
+
Index: c/src/lib/libbsp/i386/pc386/clock/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/clock/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/clock/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,54 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+PGM=${ARCH}/clock.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=ckinit rtc
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
+
+H_FILES=
+
+SRCS=$(C_FILES) $(H_FILES)
+OBJS=$(C_O_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+${PGM}: ${SRCS} ${OBJS}
+	$(make-rel)
+
+all:	${ARCH} $(SRCS) $(PGM)
+
+# the .rel file built here will be put into libbsp.a by ../wrapup/Makefile
+install:  all
Index: c/src/lib/libbsp/i386/pc386/clock/ckinit.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/clock/ckinit.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/clock/ckinit.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,285 @@
+/*-------------------------------------------------------------------------+
+| ckinit.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the PC386 clock package.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   ckinit.c,v 1.4 1995/12/19 20:07:13 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <stdlib.h>
+
+#include <bsp.h>
+#include <irq.h>
+#include <rtems/libio.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define CLOCK_IRQ  0x00  /* Clock IRQ. */
+
+/*-------------------------------------------------------------------------+
+| Macros
++--------------------------------------------------------------------------*/
+#if 0
+/* This was dropped in the last revision.  Its a nice thing to know. */
+#define TICKS_PER_SECOND() \
+          (1000000 / (Clock_isrs_per_tick * microseconds_per_isr))
+#endif /* 0 */
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+
+volatile rtems_unsigned32 Clock_driver_ticks;   /* Tick (interrupt) counter. */
+         rtems_unsigned32 Clock_isrs_per_tick;  /* ISRs per tick.            */
+         rtems_unsigned32 Clock_isrs;           /* ISRs until next tick.     */
+
+/* The following variables are set by the clock driver during its init */
+
+rtems_device_major_number rtems_clock_major = ~0;
+rtems_device_minor_number rtems_clock_minor;
+
+/*-------------------------------------------------------------------------+
+|         Function: clockIsr
+|      Description: Interrupt Service Routine for clock (08h) interruption.
+| Global Variables: Clock_driver_ticks, Clock_isrs.
+|        Arguments: vector - standard RTEMS argument - see documentation.
+|          Returns: standard return value - see documentation. 
++--------------------------------------------------------------------------*/
+static rtems_isr
+clockIsr(rtems_vector_number vector)
+{
+  /*-------------------------------------------------------------------------+
+  | PLEASE NOTE: The following is directly transcribed from the go32 BSP for
+  |              those who wish to use it with PENTIUM based machine. It needs
+  |              to be correctly integrated with the rest of the code!!!
+  +--------------------------------------------------------------------------*/
+
+#if 0 && defined(pentium) /* more accurate clock for PENTIUMs (not supported) */
+  {
+    extern long long Last_RDTSC;
+    __asm __volatile(".byte 0x0F, 0x31" : "=A" (Last_RDTSC));
+  }
+#endif /* 0 && pentium */
+
+  Clock_driver_ticks++;
+
+  if ( Clock_isrs == 1 )
+  {
+    rtems_clock_tick();
+    Clock_isrs = Clock_isrs_per_tick;
+  }
+  else
+    Clock_isrs--;
+
+  PC386_ackIrq(vector - PC386_IRQ_VECTOR_BASE);
+} /* clockIsr */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Clock_exit
+|      Description: Clock cleanup routine at RTEMS exit. NOTE: This routine is
+|                   not really necessary, since there will be a reset at exit.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void Clock_exit(void)
+{
+  if (BSP_Configuration.ticks_per_timeslice)
+  {
+    /* reset timer mode to standard (BIOS) value */
+    outport_byte(TIMER_MODE, TIMER_SEL0 | TIMER_16BIT | TIMER_RATEGEN);
+    outport_byte(TIMER_CNTR0, 0);
+    outport_byte(TIMER_CNTR0, 0);
+  }
+} /* Clock_exit */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Install_clock
+|      Description: Initialize and install clock interrupt handler.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Install_clock(rtems_isr_entry isr)
+{
+  rtems_unsigned32  microseconds_per_isr;
+
+  rtems_status_code status;
+ 
+#if 0
+  /* Initialize clock from on-board real time clock.  This breaks the  */
+  /* test code which assumes which assumes the application will do it. */
+  {
+    rtems_time_of_day now;
+
+    /* External Prototypes */
+    extern void init_rtc(void);                /* defined in 'rtc.c' */
+    extern long rtc_read(rtems_time_of_day *); /* defined in 'rtc.c' */
+
+    init_rtc();
+    if (rtc_read(&now) >= 0)
+      clock_set(&now);
+  }
+#endif /* 0 */
+
+  /* Start by assuming hardware counter is large enough, then  scale it until
+     it actually fits. */
+
+  Clock_driver_ticks  = 0;
+  Clock_isrs_per_tick = 1;
+
+  if (BSP_Configuration.microseconds_per_tick == 0)
+    microseconds_per_isr = 10000; /* default 10 ms */
+  else
+    microseconds_per_isr = BSP_Configuration.microseconds_per_tick;
+  while (US_TO_TICK(microseconds_per_isr) > 65535)
+  {
+    Clock_isrs_per_tick  *= 10;
+    microseconds_per_isr /= 10;
+  }
+
+  Clock_isrs = Clock_isrs_per_tick; /* Initialize Clock_isrs */
+
+  if (BSP_Configuration.ticks_per_timeslice)
+  {
+    /* 105/88 approximates TIMER_TICK * 1e-6 */
+    rtems_unsigned32 count = US_TO_TICK(microseconds_per_isr);
+
+    status = PC386_installRtemsIrqHandler(CLOCK_IRQ, isr);
+
+    if (status != RTEMS_SUCCESSFUL)
+    {
+      printk("Error installing clock interrupt handler!\n");
+      rtems_fatal_error_occurred(status);
+    }
+
+    outport_byte(TIMER_MODE, TIMER_SEL0|TIMER_16BIT|TIMER_RATEGEN);
+    outport_byte(TIMER_CNTR0, count >> 0 & 0xff);
+    outport_byte(TIMER_CNTR0, count >> 8 & 0xff);
+  } 
+
+  atexit(Clock_exit);
+} /* Install_clock */
+
+
+/*-------------------------------------------------------------------------+
+| Clock device driver INITIALIZE entry point.
++--------------------------------------------------------------------------+
+| Initilizes the clock driver.
++--------------------------------------------------------------------------*/
+rtems_device_driver
+Clock_initialize(rtems_device_major_number major,
+                 rtems_device_minor_number minor,
+                 void                      *pargp)
+{
+  Install_clock(clockIsr); /* Install the interrupt handler */
+ 
+  /* make major/minor avail to others such as shared memory driver */
+ 
+  rtems_clock_major = major;
+  rtems_clock_minor = minor;
+ 
+  return RTEMS_SUCCESSFUL;
+} /* Clock_initialize */
+
+
+/*-------------------------------------------------------------------------+
+| Console device driver CONTROL entry point
++--------------------------------------------------------------------------*/
+rtems_device_driver
+Clock_control(rtems_device_major_number major,
+              rtems_device_minor_number minor,
+	      void                      *pargp)
+{
+  if (pargp != NULL)
+  {
+    rtems_libio_ioctl_args_t *args = pargp;
+        
+    /*-------------------------------------------------------------------------+
+    | This is hokey, but until we get a defined interface to do this, it will
+    | just be this simple...
+    +-------------------------------------------------------------------------*/
+ 
+    if      (args->command == rtems_build_name('I', 'S', 'R', ' '))
+      clockIsr(PC386_IRQ_VECTOR_BASE + CLOCK_IRQ);
+    else if (args->command == rtems_build_name('N', 'E', 'W', ' '))
+    {
+      rtems_status_code status;
+      
+      status = PC386_installRtemsIrqHandler(CLOCK_IRQ, clockIsr);
+
+      if (status != RTEMS_SUCCESSFUL)
+      {
+	printk("Error installing clock interrupt handler!\n");
+	rtems_fatal_error_occurred(status);
+      }
+    }
+  }
+
+  return RTEMS_SUCCESSFUL;
+} /* Clock_control */
+
+
+/*-------------------------------------------------------------------------+
+| PLEASE NOTE: The following is directly transcribed from the go32 BSP for
+|              those who wish to use it with PENTIUM based machine. It needs
+|              to be correctly integrated with the rest of the code!!!
++--------------------------------------------------------------------------*/
+
+
+#if 0 && defined(pentium)
+
+/* This can be used to get extremely accurate timing on a pentium. */
+/* It isn't supported. [bryce]                                     */
+
+#define HZ 90.0
+
+volatile long long Last_RDTSC;
+
+#define RDTSC()\
+  ({ long long _now; __asm __volatile (".byte 0x0F,0x31":"=A"(_now)); _now; })
+
+long long Kernel_Time_ns( void )
+{
+  extern rtems_unsigned32 _TOD_Ticks_per_second;
+
+  unsigned  isrs_per_second = Clock_isrs_per_tick * _TOD_Ticks_per_second;
+  long long now;
+  int       flags;
+
+  disable_intr(flags);
+  now = 1e9 * Clock_driver_ticks / isrs_per_second +
+        (RDTSC() - Last_RDTSC) * (1000.0/HZ);
+  enable_intr(flags);
+  return now;
+} /* Kernel_Time_ns */
+
+#endif /* 0 && pentium */
Index: c/src/lib/libbsp/i386/pc386/clock/rtc.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/clock/rtc.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/clock/rtc.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,224 @@
+/*-------------------------------------------------------------------------+
+| rtc.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the real time clock manipulation package for the
+| PC386 board.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   rtc.c,v 1.4 1995/12/19 20:07:15 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <string.h>
+
+#include <bsp.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define IO_RTC         0x70  /* RTC                                    */
+
+#define RTC_SEC        0x00  /* seconds                                */
+#define RTC_SECALRM    0x01  /* seconds alarm                          */
+#define RTC_MIN        0x02  /* minutes                                */
+#define RTC_MINALRM    0x03  /* minutes alarm                          */
+#define RTC_HRS        0x04  /* hours                                  */
+#define RTC_HRSALRM    0x05  /* hours alarm                            */
+#define RTC_WDAY       0x06  /* week day                               */
+#define RTC_DAY        0x07  /* day of month                           */
+#define RTC_MONTH      0x08  /* month of year                          */
+#define RTC_YEAR       0x09  /* month of year                          */
+#define RTC_STATUSA    0x0a  /* status register A                      */
+#define  RTCSA_TUP     0x80  /* time update, don't look now            */
+
+#define RTC_STATUSB    0x0b  /* status register B                      */
+
+#define RTC_INTR       0x0c  /* status register C (R) interrupt source */
+#define  RTCIR_UPDATE  0x10  /* update intr                            */
+#define  RTCIR_ALARM   0x20  /* alarm intr                             */
+#define  RTCIR_PERIOD  0x40  /* periodic intr                          */
+#define  RTCIR_INT     0x80  /* interrupt output signal                */
+
+#define RTC_STATUSD    0x0d  /* status register D (R) Lost Power       */
+#define  RTCSD_PWR     0x80  /* clock lost power                       */
+
+#define RTC_DIAG       0x0e  /* status register E - bios diagnostic    */
+#define RTCDG_BITS     "\020\010clock_battery\007ROM_cksum\006config_unit\005memory_size\004fixed_disk\003invalid_time"
+
+#define RTC_CENTURY    0x32  /* current century - increment in Dec99   */
+
+
+/*-------------------------------------------------------------------------+
+| Auxiliary Functions
++--------------------------------------------------------------------------*/
+/*-------------------------------------------------------------------------+
+|         Function: bcd
+|      Description: Convert 2 digit number to its BCD representation.
+| Global Variables: None.
+|        Arguments: i - Number to convert.
+|          Returns: BCD representation of number. 
++--------------------------------------------------------------------------*/
+static inline rtems_unsigned8
+bcd(rtems_unsigned8 i)
+{
+  return ((i / 16) * 10 + (i % 16));
+} /* bcd */
+
+#define QUICK_READ  /* Quick read of the RTC: don't return number of seconds. */
+
+#ifndef QUICK_READ
+
+#define SECS_PER_DAY      (24 * 60 * 60)
+#define SECS_PER_REG_YEAR (365 * SECS_PER_DAY)
+
+/*-------------------------------------------------------------------------+
+|         Function: ytos
+|      Description: Convert years to seconds (since 1970).
+| Global Variables: None.
+|        Arguments: y - year to convert (1970 <= y <= 2100).
+|          Returns: number of seconds since 1970. 
++--------------------------------------------------------------------------*/
+static inline rtems_unsigned32
+ytos(rtems_unsigned16 y)
+{                                       /* v NUM LEAP YEARS v */
+  return ((y - 1970) * SECS_PER_REG_YEAR + (y - 1970 + 1) / 4 * SECS_PER_DAY);
+} /* ytos */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: mtos
+|      Description: Convert months to seconds since January.
+| Global Variables: None.
+|        Arguments: m - month to convert, leap - is this a month of a leap year.
+|          Returns: number of seconds since January. 
++--------------------------------------------------------------------------*/
+static inline rtems_unsigned32
+mtos(rtems_unsigned8 m, rtems_boolean leap)
+{
+  static rtems_unsigned16 daysMonth[] = { 0, 0, 31,  59,  90, 120, 151, 181,
+				               212, 243, 273, 304, 334, 365 };
+    /* Days since beginning of year until beginning of month. */
+
+  return ((daysMonth[m] + (leap ? 1 : 0)) * SECS_PER_DAY);
+} /* mtos */
+
+#endif /* QUICK_READ */
+
+/*-------------------------------------------------------------------------+
+|         Function: rtcin
+|      Description: Perform action on RTC and return its result.
+| Global Variables: None.
+|        Arguments: what - what to write to RTC port (what to do).
+|          Returns: result received from RTC port after action performed. 
++--------------------------------------------------------------------------*/
+static inline rtems_unsigned8
+rtcin(rtems_unsigned8 what)
+{
+    rtems_unsigned8 r;
+
+    outport_byte(IO_RTC,   what);
+    inport_byte (IO_RTC+1, r);
+    return r;
+} /* rtcin */
+
+
+/*-------------------------------------------------------------------------+
+| Functions
++--------------------------------------------------------------------------*/
+/*-------------------------------------------------------------------------+
+|         Function: init_rtc
+|      Description: Initialize real-time clock (RTC).
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+init_rtc(void)
+{
+  rtems_unsigned8 s;
+
+  /* initialize brain-dead battery powered clock */
+  outport_byte(IO_RTC,   RTC_STATUSA);
+  outport_byte(IO_RTC+1, 0x26);
+  outport_byte(IO_RTC,   RTC_STATUSB);
+  outport_byte(IO_RTC+1, 2);
+
+  outport_byte(IO_RTC,   RTC_DIAG);
+  inport_byte (IO_RTC+1, s);
+  if (s)
+    printk("RTC BIOS diagnostic error %b\n", s);
+
+  /* FIXME: This was last line's original version. How was it supposed to work?
+       printf("RTC BIOS diagnostic error %b\n", s, RTCDG_BITS); */
+} /* init_rtc */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: rtc_read
+|      Description: Read present time from RTC and return it.
+| Global Variables: None.
+|        Arguments: tod - to return present time in 'rtems_time_of_day' format.
+|          Returns: number of seconds from 1970/01/01 corresponding to 'tod'. 
++--------------------------------------------------------------------------*/
+long int
+rtc_read(rtems_time_of_day *tod)
+{
+  rtems_unsigned8  sa;
+  rtems_unsigned32 sec = 0;
+
+  memset(tod, 0, sizeof *tod); /* zero tod structure */
+
+  /* do we have a realtime clock present? (otherwise we loop below) */
+  sa = rtcin(RTC_STATUSA);
+  if (sa == 0xff || sa == 0)
+    return -1;
+
+  /* ready for a read? */
+  while ((sa&RTCSA_TUP) == RTCSA_TUP)
+    sa = rtcin(RTC_STATUSA);
+
+  tod->year	= bcd(rtcin(RTC_YEAR)) + 1900;  /* year    */
+  if (tod->year < 1970)	tod->year += 100;	
+  tod->month	= bcd(rtcin(RTC_MONTH));        /* month   */
+  tod->day	= bcd(rtcin(RTC_DAY));          /* day     */
+  (void)          bcd(rtcin(RTC_WDAY));         /* weekday */
+  tod->hour	= bcd(rtcin(RTC_HRS));          /* hour    */
+  tod->minute	= bcd(rtcin(RTC_MIN));          /* minutes */
+  tod->second	= bcd(rtcin(RTC_SEC));          /* seconds */
+  tod->ticks	= 0;
+
+#ifndef QUICK_READ  /* Quick read of the RTC: don't return number of seconds. */
+  sec =  ytos(tod->year);
+  sec += mtos(tod->month, (tod->year % 4) == 0);
+  sec += tod->day * SECS_PER_DAY;
+  sec += tod->hour * 60 * 60;                     /* hour    */
+  sec += tod->minute * 60;                        /* minutes */
+  sec += tod->second;                             /* seconds */
+#endif /* QUICK_READ */
+
+  return (long int)sec;
+} /* rtc_read */
+
+
Index: c/src/lib/libbsp/i386/pc386/console/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/console/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/console/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,53 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+PGM=${ARCH}/console.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=console inch outch printk
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
+
+H_FILES=
+
+SRCS=$(C_FILES) $(H_FILES)
+OBJS=$(C_O_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+${PGM}: ${SRCS} ${OBJS}
+	$(make-rel)
+
+all:	${ARCH} $(SRCS) $(PGM)
+
+# the .rel file built here will be put into libbsp.a by ../wrapup/Makefile
+install:  all
Index: c/src/lib/libbsp/i386/pc386/console/console.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/console/console.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/console/console.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,250 @@
+/*-------------------------------------------------------------------------+
+| console.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the PC386 console I/O package.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   console.c,v 1.4 1995/12/19 20:07:23 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <stdlib.h>
+
+#include <bsp.h>
+#include <irq.h>
+#include <rtems/libio.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define KEYBOARD_IRQ  0x01  /* Keyboard IRQ. */
+
+
+/*-------------------------------------------------------------------------+
+| External Prototypes
++--------------------------------------------------------------------------*/
+extern rtems_isr _IBMPC_keyboard_isr(rtems_vector_number);
+       /* keyboard (IRQ 0x01) Interrupt Service Routine (defined in 'inch.c') */
+
+
+/*-------------------------------------------------------------------------+
+| Functions
++--------------------------------------------------------------------------*/
+/*-------------------------------------------------------------------------+
+|         Function: console_cleanup
+|      Description: This routine is called at exit to clean up the console
+|                   hardware. 
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+console_cleanup(void)
+{
+  /* nothing */
+} /* console_cleanup */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: is_character_ready
+|      Description: Check if a character is available for input, and if so
+|                   return it.
+| Global Variables: None.
+|        Arguments: c - character read if available, otherwise unchanged.
+|          Returns: TRUE if there was a character available for input,
+|                   FALSE otherwise. 
++--------------------------------------------------------------------------*/
+rtems_boolean
+is_character_ready(char *c)
+{
+  return (_IBMPC_chrdy(c) ? TRUE : FALSE);
+} /* is_character_ready */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: inbyte
+|      Description: Read a character from the console (keyboard).
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Caracter read from the console. 
++--------------------------------------------------------------------------*/
+unsigned char
+inbyte(void)
+{
+  char c = _IBMPC_inch();
+
+  /* Echo character to screen */
+  _IBMPC_outch(c);
+  if (c == '\r')
+    _IBMPC_outch('\n');  /* CR = CR + LF */
+
+  return c;
+} /* inbyte */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: outbyte
+|      Description: Write a character to the console (display).
+| Global Variables: None.
+|        Arguments: Character to be written.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+outbyte(char c)
+{
+  _IBMPC_outch(c);
+} /* outbyte */
+
+
+/*-------------------------------------------------------------------------+
+| Console device driver INITIALIZE entry point.
++--------------------------------------------------------------------------+
+| Initilizes the I/O console (keyboard + VGA display) driver.
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_initialize(rtems_device_major_number major,
+                   rtems_device_minor_number minor,
+                   void                      *arg)
+{
+  rtems_status_code status;
+
+  /* Initialize video */
+  _IBMPC_initVideo();
+
+  /* Install keyboard interrupt handler */
+  status = PC386_installRtemsIrqHandler(KEYBOARD_IRQ, _IBMPC_keyboard_isr);
+
+  if (status != RTEMS_SUCCESSFUL)
+  {
+    printk("Error installing keyboard interrupt handler!\n");
+    rtems_fatal_error_occurred(status);
+  }
+
+  status =
+    rtems_io_register_name("/dev/console", major, (rtems_device_minor_number)0);
+ 
+  if (status != RTEMS_SUCCESSFUL)
+  {
+    printk("Error registering console device!\n");
+    rtems_fatal_error_occurred(status);
+  }
+ 
+  atexit(console_cleanup);
+
+  return RTEMS_SUCCESSFUL;
+} /* console_initialize */
+
+
+/*-------------------------------------------------------------------------+
+| Console device driver OPEN entry point
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_open(rtems_device_major_number major,
+             rtems_device_minor_number minor,
+             void                      *arg)
+{
+  return RTEMS_SUCCESSFUL;
+} /* console_open */
+
+
+/*-------------------------------------------------------------------------+
+| Console device driver CLOSE entry point
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_close(rtems_device_major_number major,
+              rtems_device_minor_number minor,
+              void                      *arg)
+{
+  return RTEMS_SUCCESSFUL;
+} /* console_close */
+
+ 
+/*-------------------------------------------------------------------------+
+| Console device driver READ entry point.
++--------------------------------------------------------------------------+
+| Read characters from the I/O console. We only have stdin.
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_read(rtems_device_major_number major,
+             rtems_device_minor_number minor,
+             void                      *arg)
+{
+  rtems_libio_rw_args_t *rw_args = (rtems_libio_rw_args_t *)arg;
+  char                  *buffer  = rw_args->buffer;
+  int            count, maximum  = rw_args->count;
+ 
+  for (count = 0; count < maximum; count++)
+  {
+    buffer[count] = inbyte();
+    if (buffer[count] == '\n' || buffer[count] == '\r')
+    {
+      /* What if this goes past the end of the buffer?  We're hosed. [bhc] */
+      buffer[count++]  = '\n';
+      buffer[count]    = '\0';
+      break;
+    }
+  }
+ 
+  rw_args->bytes_moved = count;
+  return ((count >= 0) ? RTEMS_SUCCESSFUL : RTEMS_UNSATISFIED);
+} /* console_read */
+ 
+
+/*-------------------------------------------------------------------------+
+| Console device driver WRITE entry point.
++--------------------------------------------------------------------------+
+| Write characters to the I/O console. Stderr and stdout are the same.
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_write(rtems_device_major_number major,
+              rtems_device_minor_number minor,
+              void                    * arg)
+{
+  rtems_libio_rw_args_t *rw_args = (rtems_libio_rw_args_t *)arg;
+  char                  *buffer  = rw_args->buffer;
+  int            count, maximum  = rw_args->count;
+ 
+  for (count = 0; count < maximum; count++)
+  {
+    outbyte(buffer[count]);
+    if (buffer[count] == '\n')
+      outbyte('\r');            /* LF = LF + CR */
+  }
+
+  rw_args->bytes_moved = maximum;
+  return RTEMS_SUCCESSFUL;
+} /* console_write */
+
+
+/*-------------------------------------------------------------------------+
+| Console device driver CONTROL entry point
++--------------------------------------------------------------------------*/
+rtems_device_driver
+console_control(rtems_device_major_number major,
+                rtems_device_minor_number minor,
+                void                      *arg)
+{
+  return RTEMS_SUCCESSFUL;
+} /* console_control */
Index: c/src/lib/libbsp/i386/pc386/console/inch.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/console/inch.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/console/inch.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,260 @@
+/*-------------------------------------------------------------------------+
+| inch.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   inch.c,v 1.3 1995/12/19 20:07:25 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+#include <bsp.h>
+#include <irq.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define KBD_CTL      0x61  /* -------------------------------- */
+#define KBD_DATA     0x60  /* Ports for PC keyboard controller */
+#define KBD_STATUS   0x64  /* -------------------------------- */
+
+#define KBD_BUF_SIZE 256
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+static char key_map[] =
+{
+  0,033,'1','2','3','4','5','6','7','8','9','0','-','=','\b','\t',
+  'q','w','e','r','t','y','u','i','o','p','[',']',015,0x80,
+  'a','s','d','f','g','h','j','k','l',';',047,0140,0x80,
+  0134,'z','x','c','v','b','n','m',',','.','/',0x80,
+  '*',0x80,' ',0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+  0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+  0x80,0x80,0x80,'0',0177
+}; /* Keyboard scancode -> character map with no modifiers.       */
+
+static char shift_map[] =
+{
+  0,033,'!','@','#','$','%','^','&','*','(',')','_','+','\b','\t',
+  'Q','W','E','R','T','Y','U','I','O','P','{','}',015,0x80,
+  'A','S','D','F','G','H','J','K','L',':',042,'~',0x80,
+  '|','Z','X','C','V','B','N','M','<','>','?',0x80,
+  '*',0x80,' ',0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+  0x80,0x80,0x80,0x80,'7','8','9',0x80,'4','5','6',0x80,
+  '1','2','3','0',177
+}; /* Keyboard scancode -> character map with SHIFT key modifier. */ 
+
+static char             kbd_buffer[KBD_BUF_SIZE];
+static rtems_unsigned16 kbd_first = 0;
+static rtems_unsigned16 kbd_last  = 0;
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_scankey
+|      Description: This function can be called during a poll for input, or by
+|                   an ISR. Basically any time you want to process a keypress.
+| Global Variables: key_map, shift_map.
+|        Arguments: outChar - character read in case of a valid reading,
+|                   otherwise unchanged.
+|          Returns: TRUE in case a valid character has been read,
+|                   FALSE otherwise.
++--------------------------------------------------------------------------*/
+rtems_boolean
+_IBMPC_scankey(char *outChar)
+{
+  unsigned char inChar;
+  static int alt_pressed   = 0;
+  static int ctrl_pressed  = 0;
+  static int shift_pressed = 0;
+  static int caps_pressed  = 0;
+  static int extended      = 0;
+
+  *outChar = NULL; /* default value if we return FALSE */
+
+  /* Read keyboard controller, toggle enable */
+  inport_byte(KBD_CTL, inChar);
+  outport_byte(KBD_CTL, inChar & ~0x80);
+  outport_byte(KBD_CTL, inChar | 0x80);
+  outport_byte(KBD_CTL, inChar & ~0x80);
+
+  /* See if it has data */
+  inport_byte(KBD_STATUS, inChar);
+  if ((inChar & 0x01) == 0)
+    return FALSE;
+
+  /* Read the data.  Handle nonsense with shift, control, etc. */
+  inport_byte(KBD_DATA, inChar);
+
+  if (extended)
+    extended--;
+
+  switch (inChar)
+  {
+    case 0xe0:
+      extended = 2;
+      return FALSE;
+      break;
+
+    case 0x38:
+      alt_pressed = 1;
+      return FALSE;
+      break;
+    case 0xb8:
+      alt_pressed = 0;
+      return FALSE;
+      break;
+
+    case 0x1d:
+      ctrl_pressed = 1;
+      return FALSE;
+      break;
+    case 0x9d:
+      ctrl_pressed = 0;
+      return FALSE;
+      break;
+
+    case 0x2a:
+      if (extended)
+        return FALSE;
+    case 0x36:
+      shift_pressed = 1;
+      return FALSE;
+      break;
+    case 0xaa:
+      if (extended)
+        return FALSE;
+    case 0xb6:
+      shift_pressed = 0;
+      return FALSE;
+      break;
+
+    case 0x3a:
+      caps_pressed = 1;
+      return FALSE;
+      break;
+    case 0xba:
+      caps_pressed = 0;
+      return FALSE;
+      break;
+
+    case 0x53:
+      if (ctrl_pressed && alt_pressed) 
+        rtemsReboot(); /* ctrl+alt+del -> reboot */
+      break;
+
+    /*
+     * Ignore unrecognized keys--usually arrow and such
+     */
+    default:
+      if ((inChar & 0x80) || (inChar > 0x39))
+      /* High-bit on means key is being released, not pressed */
+        return FALSE;
+      break;
+  } /* switch */
+
+  /* Strip high bit, look up in our map */
+  inChar &= 0x7f;
+  if (ctrl_pressed)
+  {
+    *outChar = key_map[inChar];
+    *outChar &= 037;
+  }
+  else
+  {
+    *outChar = shift_pressed ? shift_map[inChar] : key_map[inChar];
+    if (caps_pressed)
+    {
+      if (*outChar >= 'A' && *outChar <= 'Z')
+        *outChar += 'a' - 'A';
+      else if (*outChar >= 'a' && *outChar <= 'z')
+        *outChar -= 'a' - 'A';
+    }
+  }
+
+  return TRUE;
+} /* _IBMPC_scankey */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_keyboard_isr
+|      Description: Interrupt Service Routine for keyboard (0x01) IRQ.
+| Global Variables: kbd_buffer, kbd_first, kbd_last.
+|        Arguments: vector - standard RTEMS argument - see documentation.
+|          Returns: standard return value - see documentation.
++--------------------------------------------------------------------------*/
+rtems_isr
+_IBMPC_keyboard_isr(rtems_vector_number vector)
+{
+  if (_IBMPC_scankey(&kbd_buffer[kbd_last]))
+  {
+    /* Got one; save it if there is enough room in buffer. */
+    unsigned int next = (kbd_last + 1) % KBD_BUF_SIZE;
+
+    if (next != kbd_first)
+      kbd_last = next;
+  }
+
+  PC386_ackIrq(vector - PC386_IRQ_VECTOR_BASE); /* Mark interrupt as handled. */
+} /* _IBMPC_keyboard_isr */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_chrdy
+|      Description: Check keyboard ISR buffer and return character if not empty.
+| Global Variables: kbd_buffer, kbd_first, kbd_last.
+|        Arguments: c - character read if keyboard buffer not empty, otherwise
+|                   unchanged.
+|          Returns: TRUE if keyboard buffer not empty, FALSE otherwise.
++--------------------------------------------------------------------------*/
+rtems_boolean
+_IBMPC_chrdy(char *c)
+{
+  /* Check buffer our ISR builds */
+  if (kbd_first != kbd_last)
+  {
+    *c = kbd_buffer[kbd_first];
+
+    kbd_first = (kbd_first + 1) % KBD_BUF_SIZE;
+    return TRUE;
+  }
+  else
+    return FALSE;
+} /* _IBMPC_chrdy */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_inch
+|      Description: Poll keyboard until a character is ready and return it.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: character read from keyboard.
++--------------------------------------------------------------------------*/
+char
+_IBMPC_inch(void)
+{
+    char c;
+    while (!_IBMPC_chrdy(&c))
+      continue;
+
+    return c;
+} /* _IBMPC_inch */
Index: c/src/lib/libbsp/i386/pc386/console/outch.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/console/outch.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/console/outch.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,284 @@
+/*-------------------------------------------------------------------------+
+| outch.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   outch.c,v 1.4 1995/12/19 20:07:27 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <bsp.h>
+
+#include <stdlib.h>
+#include <string.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define DISPLAY_CELL_COUNT (MAX_ROW * MAX_COL)
+                                       /* Number of display cells.            */
+#define TABSIZE 4                      /* Number of spaces for TAB (\t) char. */
+#define	WHITE	0x0700                 /* White on Black background colour.   */
+#define BLANK   (WHITE | ' ')          /* Blank character.                    */
+
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+static rtems_unsigned16 *videoRam    = TVRAM;
+                           /* Physical address of start of video text memory. */
+static rtems_unsigned16 *videoRamPtr = TVRAM;
+                           /* Pointer for current output position in display. */
+static rtems_unsigned8  videoRows = MAX_ROW; /* Number of rows in display.    */
+static rtems_unsigned8  videoCols = MAX_COL; /* Number of columns in display. */
+static rtems_unsigned8  cursRow   = 0;       /* Current cursor row.           */
+static rtems_unsigned8  cursCol   = 0;       /* Current cursor column.        */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: setHardwareCursorPos
+|      Description: Set hardware video cursor at given offset into video RAM. 
+| Global Variables: None.
+|        Arguments: videoCursor - Offset into video memory.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+setHardwareCursorPos(rtems_unsigned16 videoCursor)
+{
+  outport_byte(GDC_REG_PORT, 0xe);
+  outport_byte(GDC_VAL_PORT, (videoCursor >> 8) & 0xff);
+  outport_byte(GDC_REG_PORT, 0xf);
+  outport_byte(GDC_VAL_PORT, videoCursor & 0xff);
+} /* setHardwareCursorPos */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: updateVideoRamPtr
+|      Description: Updates value of global variable "videoRamPtr" based on
+|                   current window's cursor position. 
+| Global Variables: videoRamPtr, cursRow, cursCol.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+updateVideoRamPtr(void)
+{
+  videoRamPtr = videoRam + cursRow * videoCols + cursCol;
+} /* updateVideoRamPtr */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: scrollUp
+|      Description: Scrolls display up n lines.
+| Global Variables: None.
+|        Arguments: lines - number of lines to scroll.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static void
+scrollUp(rtems_unsigned8 lines)
+{
+  rtems_unsigned16 blankCount;
+                        /* Number of blank display cells on bottom of window. */
+  rtems_unsigned16 *ptrDst, *ptrSrc;
+               /* Source and destination pointers for memory copy operations. */
+
+  if (lines < videoRows)  /* Move window's contents up. */
+  {
+    rtems_unsigned16 nonBlankCount;
+       /* Number of non-blank cells on upper part of display (total - blank). */
+
+    blankCount = lines * videoCols;
+    nonBlankCount = DISPLAY_CELL_COUNT - blankCount;
+    ptrSrc = videoRam + blankCount;
+    ptrDst = videoRam; 
+
+    while(nonBlankCount--)
+      *ptrDst++ = *ptrSrc++;
+  }
+  else                    /* Clear the whole display.   */
+  {
+    blankCount = DISPLAY_CELL_COUNT;
+    ptrDst = videoRam;
+  }
+
+  /* Fill bottom with blanks. */
+  while (blankCount-- > 0)
+    *ptrDst++ = BLANK;
+} /* scrollUp */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: printCHAR
+|      Description: Print printable character to display.
+| Global Variables: videoRamPtr, cursRow, cursCol.
+|        Arguments: c - character to write to display.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static void
+printCHAR(char c)
+{
+  *videoRamPtr++ = c | WHITE;
+  cursCol++;
+  if (cursCol == videoCols)
+  {
+    cursCol = 0;
+    cursRow++;
+    if (cursRow == videoRows)
+    {
+      cursRow--;
+      scrollUp(1);
+      videoRamPtr -= videoCols;
+    }
+  }
+} /* printCHAR */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: printBS
+|      Description: Print BS (BackSpace - '\b') character to display.
+| Global Variables: videoRamPtr, cursRow, cursCol.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+printBS(void)
+{
+  /* Move cursor back one cell. */
+  if (cursCol > 0)
+    cursCol--;
+  else if (cursRow > 0)
+  {
+    cursRow--;
+    cursCol = videoCols - 1;
+  }
+  else
+    return;
+
+  /* Write a whitespace. */
+  *(--videoRamPtr) = BLANK;
+} /* printBS */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: printHT
+|      Description: Print HT (Horizontal Tab - '\t') character to display.
+| Global Variables: cursCol.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+printHT(void)
+{
+  do
+    printCHAR(' ');
+  while (cursCol % TABSIZE);
+} /* printHT */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: printLF
+|      Description: Print LF (Line Feed  - '\n') character to display.
+| Global Variables: cursRow.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+printLF(void)
+{
+  cursRow++;
+  if (cursRow == videoRows)
+  {
+    cursRow--;
+    scrollUp(1);
+  }
+  updateVideoRamPtr();
+} /* printLF */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: printCR
+|      Description: Print CR (Carriage Return - '\r') to display.
+| Global Variables: cursCol.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static inline void
+printCR(void)
+{
+  cursCol = 0;
+  updateVideoRamPtr();
+} /* printCR */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: consPutc
+|      Description: Print a character to display at current position.
+| Global Variables: videoRamPtr, videoRam.
+|        Arguments: c - character to write to display.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static void
+consPutc(char c)
+{
+  switch (c)
+  {
+    case '\b': printBS();    break;
+    case '\t': printHT();    break;
+    case '\n': printLF();    break;
+    case '\r': printCR();    break;
+    default:   printCHAR(c); break;
+  } /* switch */
+
+  setHardwareCursorPos(videoRamPtr - videoRam);
+                                           /* At current offset into videoRam */
+} /* consPutc */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_outch
+|      Description: Higher level (console) interface to consPutc.
+| Global Variables: None.
+|        Arguments: c - character to write to console.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+_IBMPC_outch(char c)
+{
+  consPutc(c);
+} /* _IBMPC_outch */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _IBMPC_initVideo
+|      Description: Video system initialization. Hook for any early setup.
+| Global Variables: videoRows.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+_IBMPC_initVideo(void)
+{
+  scrollUp(videoRows);     /* Clear entire screen         */
+  setHardwareCursorPos(0); /* Cursor at upper left corner */
+} /* _IBMPC_initVideo */
Index: c/src/lib/libbsp/i386/pc386/include/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/include/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/include/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,32 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+H_FILES = $(srcdir)/bsp.h $(srcdir)/coverhd.h  $(srcdir)/irq.h
+
+#
+#  Equate files are for including from assembly preprocessed by
+#  gm4 or gasp.  No examples are provided except for those for
+#  other CPUs.  The best way to generate them would be to
+#  provide a program which generates the constants used based
+#  on the C equivalents.
+#
+
+EQ_FILES =
+
+SRCS=$(H_FILES) $(EQ_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+all:	$(SRCS)
+	$(INSTALL) -m 444 $(H_FILES) $(PROJECT_INCLUDE)
+	$(INSTALL) -m 444 $(EQ_FILES) $(PROJECT_INCLUDE)
Index: c/src/lib/libbsp/i386/pc386/include/bsp.h
===================================================================
--- c/src/lib/libbsp/i386/pc386/include/bsp.h	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/include/bsp.h	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,192 @@
+/*-------------------------------------------------------------------------+
+| bsp.h v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This include file contains definitions related to the PC386 BSP.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   bsp.h,v 1.5 1995/12/19 20:07:30 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#ifndef __BSP_H_
+#define __BSP_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <rtems.h>
+#include <iosupp.h>
+#include <console.h>
+#include <clockdrv.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define BSP_LIBIO_MAX_FDS 20             /* Number of libio files we want.    */
+
+/*-------------------------------------------------------------------------+
+| 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. */
+
+/*-------------------------------------------------------------------------+
+| Video (console) related constants.
++--------------------------------------------------------------------------*/
+#define COLOUR  1  /* Assume colour console */
+
+#if COLOUR
+
+# define        GDC_REG_PORT    0x3D4
+# define        GDC_VAL_PORT    0x3D5
+# define        TVRAM           ((rtems_unsigned16 *)0xB8000)
+
+#else
+
+# define        GDC_REG_PORT    0x3B4
+# define        GDC_VAL_PORT    0x3B5
+# define        TVRAM           ((rtems_unsigned16 *)0xB0000)
+
+#endif /* COLOUR */
+
+/* Number of Video Lines & Columns */
+
+#define MAX_COL 80
+
+#ifdef RTEMS_VIDEO_80x50
+#define MAX_ROW 50
+#else
+#define MAX_ROW 25
+#endif /* RTEMS_VIDEO_80x50 */
+
+/*-------------------------------------------------------------------------+
+| Constants relating to the 8254 (or 8253) programmable interval timers.
++--------------------------------------------------------------------------*/
+#define IO_TIMER1      0x40
+                  /* Port address of the control port and timer channels */
+#define TIMER_CNTR0    (IO_TIMER1 + 0) /* timer 0 counter port           */
+#define TIMER_CNTR1    (IO_TIMER1 + 1) /* timer 1 counter port           */
+#define TIMER_CNTR2    (IO_TIMER1 + 2) /* timer 2 counter port           */
+#define TIMER_MODE     (IO_TIMER1 + 3) /* timer mode port                */
+#define TIMER_SEL0     0x00            /* select counter 0               */
+#define TIMER_SEL1     0x40            /* select counter 1               */
+#define TIMER_SEL2     0x80            /* select counter 2               */
+#define TIMER_INTTC    0x00            /* mode 0, intr on terminal cnt   */
+#define TIMER_ONESHOT  0x02            /* mode 1, one shot               */
+#define TIMER_RATEGEN  0x04            /* mode 2, rate generator         */
+#define TIMER_SQWAVE   0x06            /* mode 3, square wave            */
+#define TIMER_SWSTROBE 0x08            /* mode 4, s/w triggered strobe   */
+#define TIMER_HWSTROBE 0x0a            /* mode 5, h/w triggered strobe   */
+#define TIMER_LATCH    0x00            /* latch counter for reading      */
+#define TIMER_LSB      0x10            /* r/w counter LSB                */
+#define TIMER_MSB      0x20            /* r/w counter MSB                */
+#define TIMER_16BIT    0x30            /* r/w counter 16 bits, LSB first */
+#define TIMER_BCD      0x01            /* count in BCD                   */
+
+#define	TIMER_TICK     1193182  /* The internal tick rate in ticks per second */
+
+/*-------------------------------------------------------------------------+
+| Define the time limits for RTEMS Test Suite test durations. Long test and
+| short test duration limits are provided. These values are in seconds and
+| need to be converted to ticks for the application.
++--------------------------------------------------------------------------*/
+#define MAX_LONG_TEST_DURATION       300  /* 5 minutes = 300 seconds */
+#define MAX_SHORT_TEST_DURATION      3    /* 3 seconds */
+
+/*-------------------------------------------------------------------------+
+| Macros
++--------------------------------------------------------------------------*/
+/*-------------------------------------------------------------------------+
+| Define the interrupt mechanism for Time Test 27.
+| NOTE: Use a software interrupt for the i386 family.
++--------------------------------------------------------------------------*/
+#define MUST_WAIT_FOR_INTERRUPT 0
+#define Install_tm27_vector(handler) \
+{ \
+  rtems_isr_entry dummy; \
+  rtems_interrupt_catch(handler, 0x90, &dummy); \
+}
+#define Cause_tm27_intr() asm volatile("int $0x90" : :);
+#define Clear_tm27_intr()
+#define Lower_tm27_intr()
+
+/*-------------------------------------------------------------------------+
+| Simple spin delay in microsecond units for device drivers.
+| This is very dependent on the clock speed of the target.
++--------------------------------------------------------------------------*/
+#define delay(_microseconds) \
+{ \
+  rtems_unsigned32 _cnt = _microseconds; \
+  asm volatile ("0: nop; mov %0,%0; loop 0b" : "=c"(_cnt) : "0"(_cnt)); \
+}
+
+/*-------------------------------------------------------------------------+
+| Convert microseconds to ticks and ticks to microseconds.
++--------------------------------------------------------------------------*/
+#define US_TO_TICK(us) (((us)*105+44)/88)
+#define TICK_TO_US(tk) (((tk)*88+52)/105)
+
+/*-------------------------------------------------------------------------+
+| External Variables.
++--------------------------------------------------------------------------*/
+extern i386_IDT_slot Interrupt_descriptor_table[256];
+extern i386_GDT_slot Global_descriptor_table   [8192];
+ 
+extern rtems_configuration_table BSP_Configuration;
+                                    /* User provided BSP configuration table. */
+extern rtems_unsigned32          rtemsFreeMemStart;
+  /* Address of start of free memory - should be used when creating new
+     partitions or regions and updated afterwards. */
+
+/*-------------------------------------------------------------------------+
+| Function Prototypes.
++--------------------------------------------------------------------------*/
+void          _IBMPC_initVideo(void);    /* from 'outch.c'  */
+void          _IBMPC_outch    (char);    /* from 'outch.c'  */
+rtems_boolean _IBMPC_chrdy    (char *);  /* from 'inch.c'   */
+char          _IBMPC_inch     (void);    /* from 'inch.c'   */ 
+
+void printk(char *fmt, ...);             /* from 'printk.c' */
+
+void rtemsReboot(void);                  /* from 'exit.c'   */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __BSP_H_ */
+/* end of include file */
Index: c/src/lib/libbsp/i386/pc386/include/coverhd.h
===================================================================
--- c/src/lib/libbsp/i386/pc386/include/coverhd.h	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/include/coverhd.h	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,104 @@
+/* coverhd.h
+ *
+ *  This include file has defines to represent the overhead associated
+ *  with calling a particular directive from C on this target.
+ *
+ *  COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.
+ *  On-Line Applications Research Corporation (OAR).
+ *  All rights assigned to U.S. Government, 1994.
+ *
+ *  This material may be reproduced by or for the U.S. Government pursuant
+ *  to the copyright license under the clause at DFARS 252.227-7013.  This
+ *  notice must appear in all copies of this file and its derivatives.
+ *
+ *  coverhd.h,v 1.2 1995/12/19 20:07:32 joel Exp
+ */
+
+#ifndef __COVERHD_h
+#define __COVERHD_h
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define CALLING_OVERHEAD_INITIALIZE_EXECUTIVE      0
+#define CALLING_OVERHEAD_SHUTDOWN_EXECUTIVE        0
+#define CALLING_OVERHEAD_TASK_CREATE               0
+#define CALLING_OVERHEAD_TASK_IDENT                0
+#define CALLING_OVERHEAD_TASK_START                0
+#define CALLING_OVERHEAD_TASK_RESTART              0
+#define CALLING_OVERHEAD_TASK_DELETE               0
+#define CALLING_OVERHEAD_TASK_SUSPEND              0
+#define CALLING_OVERHEAD_TASK_RESUME               0
+#define CALLING_OVERHEAD_TASK_SET_PRIORITY         0
+#define CALLING_OVERHEAD_TASK_MODE                 0
+#define CALLING_OVERHEAD_TASK_GET_NOTE             0
+#define CALLING_OVERHEAD_TASK_SET_NOTE             0
+#define CALLING_OVERHEAD_TASK_WAKE_WHEN            0
+#define CALLING_OVERHEAD_TASK_WAKE_AFTER           0
+#define CALLING_OVERHEAD_INTERRUPT_CATCH           0
+#define CALLING_OVERHEAD_CLOCK_GET                 0
+#define CALLING_OVERHEAD_CLOCK_SET                 0
+#define CALLING_OVERHEAD_CLOCK_TICK                0
+
+#define CALLING_OVERHEAD_TIMER_CREATE              0
+#define CALLING_OVERHEAD_TIMER_IDENT               0
+#define CALLING_OVERHEAD_TIMER_DELETE              0
+#define CALLING_OVERHEAD_TIMER_FIRE_AFTER          0
+#define CALLING_OVERHEAD_TIMER_FIRE_WHEN           0
+#define CALLING_OVERHEAD_TIMER_RESET               0
+#define CALLING_OVERHEAD_TIMER_CANCEL              0
+#define CALLING_OVERHEAD_SEMAPHORE_CREATE          0
+#define CALLING_OVERHEAD_SEMAPHORE_DELETE          0
+#define CALLING_OVERHEAD_SEMAPHORE_IDENT           0
+#define CALLING_OVERHEAD_SEMAPHORE_OBTAIN          0
+#define CALLING_OVERHEAD_SEMAPHORE_RELEASE         0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_CREATE      0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_IDENT       0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_DELETE      0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_SEND        0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_URGENT      0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_BROADCAST   0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_RECEIVE     0
+#define CALLING_OVERHEAD_MESSAGE_QUEUE_FLUSH       0
+
+#define CALLING_OVERHEAD_EVENT_SEND                0
+#define CALLING_OVERHEAD_EVENT_RECEIVE             0
+#define CALLING_OVERHEAD_SIGNAL_CATCH              0
+#define CALLING_OVERHEAD_SIGNAL_SEND               0
+#define CALLING_OVERHEAD_PARTITION_CREATE          0
+#define CALLING_OVERHEAD_PARTITION_IDENT           0
+#define CALLING_OVERHEAD_PARTITION_DELETE          0
+#define CALLING_OVERHEAD_PARTITION_GET_BUFFER      0
+#define CALLING_OVERHEAD_PARTITION_RETURN_BUFFER   0
+#define CALLING_OVERHEAD_REGION_CREATE             0
+#define CALLING_OVERHEAD_REGION_IDENT              0
+#define CALLING_OVERHEAD_REGION_DELETE             0
+#define CALLING_OVERHEAD_REGION_GET_SEGMENT        0
+#define CALLING_OVERHEAD_REGION_RETURN_SEGMENT     0
+#define CALLING_OVERHEAD_PORT_CREATE               0
+#define CALLING_OVERHEAD_PORT_IDENT                0
+#define CALLING_OVERHEAD_PORT_DELETE               0
+#define CALLING_OVERHEAD_PORT_EXTERNAL_TO_INTERNAL 0
+#define CALLING_OVERHEAD_PORT_INTERNAL_TO_EXTERNAL 0
+
+#define CALLING_OVERHEAD_IO_INITIALIZE             0
+#define CALLING_OVERHEAD_IO_OPEN                   0
+#define CALLING_OVERHEAD_IO_CLOSE                  0
+#define CALLING_OVERHEAD_IO_READ                   0
+#define CALLING_OVERHEAD_IO_WRITE                  0
+#define CALLING_OVERHEAD_IO_CONTROL                0
+#define CALLING_OVERHEAD_FATAL_ERROR_OCCURRED      0
+#define CALLING_OVERHEAD_RATE_MONOTONIC_CREATE     0
+#define CALLING_OVERHEAD_RATE_MONOTONIC_IDENT      0
+#define CALLING_OVERHEAD_RATE_MONOTONIC_DELETE     0
+#define CALLING_OVERHEAD_RATE_MONOTONIC_CANCEL     0
+#define CALLING_OVERHEAD_RATE_MONOTONIC_PERIOD     0
+#define CALLING_OVERHEAD_MULTIPROCESSING_ANNOUNCE  0
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+/* end of include file */
Index: c/src/lib/libbsp/i386/pc386/start/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/start/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/start/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,56 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+PGMS=${ARCH}/start.o
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
+
+H_FILES=
+
+# Assembly source names, if any, go here -- minus the .s
+S_PIECES=start
+S_FILES=$(S_PIECES:%=%.s)
+S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
+
+SRCS=$(C_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+all:	${ARCH} $(SRCS) $(OBJS) $(PGM)
+	$(INSTALL_VARIANT) -m 555 ${PGMS} ${PROJECT_RELEASE}/lib
+
+# Install the program(s), appending _g or _p as appropriate.
+# for include files, just use $(INSTALL)
Index: c/src/lib/libbsp/i386/pc386/start/start.s
===================================================================
--- c/src/lib/libbsp/i386/pc386/start/start.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/start/start.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,416 @@
+/*-------------------------------------------------------------------------+
+| start.s v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the entry point for the application.
+| The name of this entry point is compiler dependent.
+| It jumps to the BSP which is responsible for performing all initialization.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on an earlier generation RTEMS i386 start.s and the
+| following copyright applies:
+|
+| **************************************************************************
+| *  COPYRIGHT (c) 1989-1997.
+| *  On-Line Applications Research Corporation (OAR). 
+| *  Copyright assigned to U.S. Government, 1994.
+| *
+| *  The license and distribution terms for this file may be
+| *  found in the file LICENSE in this distribution or at
+| *  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>
++--------------------------------------------------------------------------*/
+
+
+#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:	
++----------------------------------------------------------------------------*/
+
+.set DTR_LIMIT, 0		# offset of two byte limit
+.set DTR_BASE,  2		# offset of four byte base address
+.set DTR_SIZE,  6		# size of DTR register
+
+/*----------------------------------------------------------------------------+
+| CODE section
++----------------------------------------------------------------------------*/
+
+BEGIN_CODE
+
+	PUBLIC (start)		# GNU default entry point
+
+	EXTERN (main)
+	EXTERN (load_segments)
+	EXTERN (exit)
+
+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
+        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
+| other board specific initialization procedures. 
+|
+| NOTE: Upon return, gs will contain the segment descriptor for a segment which
+|       maps directly to all of physical memory.
++----------------------------------------------------------------------------*/
+
+	jmp	SYM (_load_segments)	# load board dependent segments
+
+/*----------------------------------------------------------------------------+
+| Set up the stack
++----------------------------------------------------------------------------*/
+
+	PUBLIC (_establish_stack)
+SYM (_establish_stack):
+
+	movl	$_end, eax		# eax = end of bss/start of heap
+	addl	$heap_size, eax		# eax = end of heap
+	movl	eax, stack_start	# Save for brk() routine
+	addl	$stack_size, eax	# make room for stack
+	andl	$0xffffffc0, eax	# align it on 16 byte boundary
+	movl	eax, esp		# set stack pointer
+	movl	eax, ebp		# set base pointer
+
+/*----------------------------------------------------------------------------+
+| Zero out the BSS segment
++----------------------------------------------------------------------------*/
+
+SYM (zero_bss):
+	cld				# make direction flag count up
+	movl	$ SYM (_end), ecx	# find end of .bss
+	movl	$ SYM (_bss_start), edi	# edi = beginning of .bss
+	subl	edi, ecx		# ecx = size of .bss in bytes
+	shll	ecx			# size of .bss in longs
+	xorl	eax, eax		# value to clear out memory
+	repne				# while ecx != 0
+	stosl				#   clear a long in the bss
+
+	/*---------------------------------------------------------------------+
+	| Copy the Global Descriptor Table to our space
+	+---------------------------------------------------------------------*/
+
+	sgdt	SYM (_Original_GDTR)	# save original GDT
+	movzwl	SYM (_Original_GDTR)+DTR_LIMIT, ecx	# size of GDT in bytes;
+					# limit is 8192 entries * 8 bytes per
+
+	/*---------------------------------------------------------------------+
+	| make ds:esi point to the original GDT
+	+---------------------------------------------------------------------*/
+
+	movl	SYM (_Original_GDTR)+DTR_BASE, esi
+	push	ds			# save ds
+	movw	gs, ax
+	movw	ax, ds
+
+	/*---------------------------------------------------------------------+
+	| make es:edi point to the new (our copy) GDT
+	+---------------------------------------------------------------------*/
+
+	movl	$ SYM (_Global_descriptor_table), edi
+
+	rep
+	movsb				# copy the GDT (ds:esi -> es:edi)
+
+	pop	ds			# restore ds
+
+	/*---------------------------------------------------------------------+
+	| Build and load new contents of GDTR
+	+---------------------------------------------------------------------*/
+
+	movw	SYM (_Original_GDTR)+DTR_LIMIT, ecx	# set new limit
+	movw	cx, SYM (_New_GDTR)+DTR_LIMIT
+
+	push	$ SYM (_Global_descriptor_table)
+	push	es
+	call	SYM (i386_Logical_to_physical)
+	addl	$6, esp
+	movl	eax, SYM (_New_GDTR)+DTR_BASE	# set new base
+
+	cmpb	$0, SYM (_Do_Load_GDT)	# Should the new GDT be loaded?
+	je	SYM (no_gdt_load)	# NO, then branch
+	lgdt	SYM (_New_GDTR)		# load the new GDT
+
+SYM (no_gdt_load):
+
+	/*---------------------------------------------------------------------+
+	| Copy the Interrupt Descriptor Table to our space
+	+---------------------------------------------------------------------*/
+
+	sidt	SYM (_Original_IDTR)	# save original IDT
+	movzwl	SYM (_Original_IDTR)+DTR_LIMIT, ecx	# size of IDT in bytes;
+					#limit is 256 entries * 8 bytes per
+
+	/*---------------------------------------------------------------------+
+	| make ds:esi point to the original IDT
+	+---------------------------------------------------------------------*/
+
+	movl	SYM (_Original_IDTR)+DTR_BASE, esi
+
+	push	ds			# save ds
+	movw	gs, ax
+	movw	ax, ds
+
+	/*---------------------------------------------------------------------+
+	| make es:edi point to the new (our copy) IDT
+	+---------------------------------------------------------------------*/
+
+	movl	$ SYM (Interrupt_descriptor_table), edi
+
+	rep
+	movsb				# copy the IDT (ds:esi -> es:edi)
+	pop	ds			# restore ds
+
+	/*---------------------------------------------------------------------+
+	| Build and load new contents of IDTR
+	+---------------------------------------------------------------------*/
+
+	movw	SYM (_Original_IDTR+DTR_LIMIT), ecx	# set new limit
+	movw	cx, SYM (_New_IDTR)+DTR_LIMIT
+
+	push	$ SYM (Interrupt_descriptor_table)
+	push	es
+	call	SYM (i386_Logical_to_physical)
+	addl	$6, esp
+	movl	eax, SYM (_New_IDTR)+DTR_BASE		# set new base
+
+	cmpb	$0, SYM (_Do_Load_IDT)	# Should the new IDT be loaded?
+	je	SYM (no_idt_load)	# NO, then branch
+	lidt	SYM (_New_IDTR)		# load the new IDT
+SYM (no_idt_load):
+
+	/*---------------------------------------------------------------------+
+	| Initialize the i387.
+	|
+	| Using the NO WAIT form of the instruction insures that if it is not
+	| present the board will not lock up or get an exception.
+	+---------------------------------------------------------------------*/
+
+	fninit				# MUST USE NO-WAIT FORM
+
+	/*---------------------------------------------------------------------+
+	| Transfer control to User's Board Support Package
+	+---------------------------------------------------------------------*/
+
+	pushl	$0			# environp
+	pushl	$0			# argv
+        pushl	$0			# argc
+	call	SYM (main)
+	addl	$12, esp
+
+	/*---------------------------------------------------------------------+
+	| Clean up
+	+---------------------------------------------------------------------*/
+
+	EXTERN (return_to_monitor)
+
+	PUBLIC (Bsp_cleanup)
+
+SYM (Bsp_cleanup):
+
+	cmpb	$0, SYM (_Do_Load_IDT)	# Was the new IDT loaded?
+	je	SYM (no_idt_restore)	# NO, then branch
+	lidt	SYM (_Original_IDTR)	# restore the new IDT
+
+SYM (no_idt_restore):
+
+	cmpb	$0, SYM (_Do_Load_GDT)	# Was the new GDT loaded?
+	je	SYM (no_gdt_restore)	# NO, then branch
+	lgdt    SYM (_Original_GDTR)	# restore the new GDT
+
+SYM (no_gdt_restore):
+
+	jmp	SYM (_return_to_monitor)
+
+END_CODE
+
+/*----------------------------------------------------------------------------+
+| DATA section
++----------------------------------------------------------------------------*/
+
+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_GDT)	# defined in the BSP
+
+	.align	2
+	PUBLIC (start_frame)
+SYM (start_frame):
+	.long	0
+
+	PUBLIC (stack_start)
+SYM (stack_start):
+	.long	0
+
+END_DATA
+
+/*----------------------------------------------------------------------------+
+| BSS section
++----------------------------------------------------------------------------*/
+
+BEGIN_BSS
+
+	PUBLIC (heap_size)
+	.set	heap_size, 0x2000
+
+	PUBLIC (stack_size)
+	.set	stack_size, 0x1000
+
+	PUBLIC (Interrupt_descriptor_table)
+SYM (Interrupt_descriptor_table):
+	.space (256 * 8)	# reserve space for all 256 interrupts
+
+	PUBLIC (_Original_IDTR)
+SYM (_Original_IDTR):
+	.space DTR_SIZE
+
+	PUBLIC (_New_IDTR)
+SYM (_New_IDTR):
+	.space DTR_SIZE
+
+	PUBLIC (_Global_descriptor_table)
+SYM (_Global_descriptor_table):
+#ifdef pc386
+	
+	.space (3 * 8)	# the PC386 bsp only needs 3 segment descriptors:
+#else			#   NULL, CODE and DATA
+	.space (8192 * 8)
+	
+#endif /* pc386 */
+
+	PUBLIC (_Original_GDTR)
+SYM (_Original_GDTR):
+	.space DTR_SIZE
+
+	PUBLIC (_New_GDTR)
+SYM (_New_GDTR):
+	.space DTR_SIZE
+
+	PUBLIC (_Physical_base_of_ds)
+SYM (_Physical_base_of_ds):
+	.space 4
+
+	PUBLIC (_Physical_base_of_cs)
+SYM (_Physical_base_of_cs):
+	.space 4
+
+END_BSS
+
+END
Index: c/src/lib/libbsp/i386/pc386/startup/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,58 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@:@srcdir@/../../../shared
+
+PGM=${ARCH}/startup.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=bspstart exit irq sbrk 
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
+
+H_FILES=
+
+# Assembly source names, if any, go here -- minus the .s
+S_PIECES=ldsegs
+S_FILES=$(S_PIECES:%=%.s)
+S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
+
+SRCS=$(srcdir)/linkcmds $(C_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+${PGM}: ${SRCS} ${OBJS}
+	$(make-rel)
+all:	${ARCH} $(SRCS) $(PGM)
+	$(INSTALL) $(srcdir)/linkcmds ${PROJECT_RELEASE}/lib
+
+# the .rel file built here will be put into libbsp.a by ../wrapup/Makefile
+
Index: c/src/lib/libbsp/i386/pc386/startup/bspstart.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/bspstart.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/bspstart.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,241 @@
+/*-------------------------------------------------------------------------+
+| bspstart.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the PC386 BSP startup package. It includes application,
+| board, and monitor specific initialization and configuration. The generic CPU
+| dependent initialization has been performed before this routine is invoked. 
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   bspstart.c,v 1.8 1996/05/28 13:12:40 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <fcntl.h>
+
+#include <bsp.h>
+#include <libcsupport.h>
+#include <rtems/libio.h>
+ 
+#ifdef STACK_CHECKER_ON
+#include <stackchk.h>
+#endif
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+#ifdef RTEMS_SMALL_MEMORY
+extern rtems_unsigned32 _end;           /* End of BSS. Defined in 'linkcmds'. */
+
+rtems_unsigned32 rtemsFreeMemStart = (rtems_unsigned32)&_end;
+                         /* Address of start of free memory - should be updated
+                            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
+   with some changes. */
+
+extern rtems_configuration_table  Configuration;
+       rtems_configuration_table  BSP_Configuration;
+
+rtems_cpu_table Cpu_table;                     /* CPU configuration table.    */
+char            *rtems_progname;               /* Program name - from main(). */
+
+
+/*-------------------------------------------------------------------------+
+| External Prototypes
++--------------------------------------------------------------------------*/
+extern void _exit(int);  /* define in exit.c */
+
+/*-------------------------------------------------------------------------+
+|         Function: bsp_libc_init
+|      Description: Initialize whatever libc we are using. Called from
+|                   pretasking hook. 
+| Global Variables: rtemsFreeMemStart.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+static void
+bsp_libc_init(void)
+{
+  if (rtemsFreeMemStart & (CPU_ALIGNMENT - 1))  /* not aligned => align it */
+    rtemsFreeMemStart = (rtemsFreeMemStart+CPU_ALIGNMENT) & ~(CPU_ALIGNMENT-1);
+
+  RTEMS_Malloc_Initialize((void *)rtemsFreeMemStart, HEAP_SIZE << 10, 0);
+  rtemsFreeMemStart += HEAP_SIZE << 10;           /* HEAP_SIZE is in KBytes */
+
+  /* Init the RTEMS libio facility to provide UNIX-like system calls for use by
+     newlib (ie: provide __rtems_open, __rtems_close, etc). Uses malloc()
+     to get area for the iops, so must be after malloc initialization. */
+
+  rtems_libio_init();
+
+  /* Set up for the libc handling. */
+
+  if (BSP_Configuration.ticks_per_timeslice > 0)
+    libc_init(1); /* reentrant if possible */
+  else
+    libc_init(0); /* non-reentrant         */
+} /* bsp_libc_init */
+
+ 
+/*-------------------------------------------------------------------------+
+|         Function: bsp_pretasking_hook
+|      Description: BSP pretasking hook.  Called just before drivers are
+|                   initialized. Used to setup libc and install any BSP
+|                   extensions. NOTE: Must not use libc (to do io) from here,
+|                   since drivers are not yet initialized.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+bsp_pretasking_hook(void)
+{
+  bsp_libc_init();
+
+#ifdef STACK_CHECKER_ON
+  /* Initialize the stack bounds checker. We can either turn it on here or from
+     the app. */
+   
+  Stack_check_Initialize();
+
+#endif /* STACK_CHECKER_ON */
+ 
+#ifdef RTEMS_DEBUG
+
+  rtems_debug_enable(RTEMS_DEBUG_ALL_MASK);
+
+#endif /* RTEMS_DEBUG */
+} /* bsp_pretasking_hook */
+ 
+
+/*-------------------------------------------------------------------------+
+|         Function: bsp_postdriver_hook
+|      Description: After drivers are setup, register some "filenames" and open
+|                   stdin, stdout, stderr files. Newlib will automatically
+|                   associate the files with these (it hardcodes the numbers).
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+bsp_postdriver_hook(void)
+{
+  int stdin_fd, stdout_fd, stderr_fd;
+
+  rtems_status_code error_code;
+ 
+  error_code = 'S' << 24 | 'T' << 16;
+
+  /* open standard devices: stdout, stderr and stdin */
+ 
+  if ((stdin_fd =  __rtems_open("/dev/console", O_RDONLY, 0)) < 0)
+    rtems_fatal_error_occurred( error_code | 'D' << 8 | '0' );
+ 
+  if ((stdout_fd = __rtems_open("/dev/console", O_WRONLY, 0)) < 0)
+    rtems_fatal_error_occurred( error_code | 'D' << 8 | '1' );
+ 
+  if ((stderr_fd = __rtems_open("/dev/console", O_WRONLY, 0)) < 1)
+    rtems_fatal_error_occurred( error_code | 'D' << 8 | '2' );
+ 
+  if ((stdin_fd != 0) || (stdout_fd != 1) || (stderr_fd != 2))
+    rtems_fatal_error_occurred( error_code | 'I' << 8 | 'O' );
+} /* bsp_postdriver_hook */ 
+
+
+/*-------------------------------------------------------------------------+
+|         Function: main
+|      Description: Called from bsp's startup code ('start.s').
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+int main(int argc, char **argv, char **environp)
+{
+  /* If we don't have command line arguments set default program name. */
+
+  if ((argc > 0) && argv && argv[0])
+    rtems_progname = argv[0];
+  else
+    rtems_progname = "RTEMS";
+
+  Cpu_table.pretasking_hook         = bsp_pretasking_hook; /* init libc, etc. */
+  Cpu_table.predriver_hook          = NULL;                /* use system's    */
+  Cpu_table.postdriver_hook         = bsp_postdriver_hook;
+  Cpu_table.idle_task               = NULL;
+                                          /* do not override system IDLE task */
+  Cpu_table.do_zero_of_workspace    = TRUE;
+  Cpu_table.interrupt_table_segment = get_ds();
+  Cpu_table.interrupt_table_offset  = (void *)Interrupt_descriptor_table;
+  Cpu_table.interrupt_stack_size    = 4096;
+  Cpu_table.extra_mpci_receive_server_stack = 0;
+
+  /* Copy user's table and make necessary adjustments.              */
+
+  BSP_Configuration = Configuration;
+
+  /* Place RTEMS workspace at top of physical RAM (RAM_END defined in 'bsp.h' */
+
+  BSP_Configuration.work_space_start =
+                          (void *)(RAM_END - BSP_Configuration.work_space_size);
+
+  /* Add 1 region for Malloc in libc_low.                           */
+
+  BSP_Configuration.RTEMS_api_configuration->maximum_regions++;
+
+  /* Add 1 extension for newlib libc.                               */
+
+#ifdef RTEMS_NEWLIB
+  BSP_Configuration.maximum_extensions++;
+#endif
+
+  /* Add another extension if using the stack checker.              */
+
+#ifdef STACK_CHECKER_ON
+  BSP_Configuration.maximum_extensions++;
+#endif
+
+  /* Tell libio how many fd's we want and allow it to tweak config. */
+
+  rtems_libio_config(&BSP_Configuration, BSP_LIBIO_MAX_FDS);
+
+  rtems_initialize_executive(&BSP_Configuration, &Cpu_table);
+  /* does not return */
+
+  /*-------------------------------------------------------------------------+
+  | We only return here if the executive has finished. This happens when the
+  | task has called exit(). We will then call _exit() which is part of the bsp.
+  +--------------------------------------------------------------------------*/
+
+  for (;;)
+    _exit(0);
+
+  /* no cleanup necessary for PC386 */
+
+  return 0;
+} /* main */
Index: c/src/lib/libbsp/i386/pc386/startup/exit.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/exit.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/exit.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,73 @@
+/*-------------------------------------------------------------------------+
+| exit.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| Routines to shutdown and reboot the PC.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   exit.c,v 1.2 1995/12/19 20:07:36 joel Exp -  go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <stdio.h>
+
+#include <bsp.h>
+
+/*-------------------------------------------------------------------------+
+| External Prototypes
++--------------------------------------------------------------------------*/
+extern rtems_boolean _IBMPC_scankey(char *);  /* define in 'inch.c' */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: rtemsReboot
+|      Description: Reboot the PC. 
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+inline void rtemsReboot(void)
+{
+  /* shutdown and reboot */
+  outport_byte(0x64, 0xFE);        /* use keyboard controler to do the job... */
+} /* rtemsReboot */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: _exit
+|      Description: Shutdown the PC. Called from libc's 'exit'. 
+| Global Variables: None.
+|        Arguments: status - exit status (ignored).
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void _exit(int status)
+{
+  unsigned char ch;
+  puts("\nEXECUTIVE SHUTDOWN! Any key to reboot...");
+
+  while(!_IBMPC_scankey(&ch))
+    ;
+
+  rtemsReboot();
+} /* _exit */
Index: c/src/lib/libbsp/i386/pc386/startup/ldsegs.s
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/ldsegs.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/ldsegs.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,205 @@
+/*-------------------------------------------------------------------------+
+| ldsegs.s v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file assists the board independent startup code by loading the proper
+| segment register values. The values loaded are board dependent. In addition
+| it contains code to enable the A20 line and to reprogram the PIC to relocate
+| the IRQ interrupt vectors to 0x20 -> 0x2f.
+| NOTE: No stack has been established when this routine is invoked.
+|	It returns by jumping back to bspentry.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is base on:
+|   ldsegs.s,v 1.4 1996/04/20 16:48:30 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
+|
+| Also based on (from the Linux source tree):
+|   setup.S - Copyright (C) 1991, 1992 Linus Torvalds
++--------------------------------------------------------------------------*/
+
+
+#include "asm.h"
+
+/*----------------------------------------------------------------------------+
+| Constants
++----------------------------------------------------------------------------*/
+.set	PROT_DATA_SEG, 0x10	# offset in gdt
+.set	RESET_SS, PROT_DATA_SEG	# initial value of stack segment register
+.set	RESET_DS, PROT_DATA_SEG	# initial value of data segment register
+.set	RESET_ES, PROT_DATA_SEG	# initial value of extra segment register
+.set	RESET_FS, PROT_DATA_SEG	# initial value of "f" segment register
+.set	RESET_GS, PROT_DATA_SEG	# initial value of "g" segment register
+
+
+/*----------------------------------------------------------------------------+
+| Macros
++----------------------------------------------------------------------------*/
+#define LOAD_SEGMENTS(_value, _segment) \
+	movw	$ ## _value, ax; \
+	movw	ax, _segment
+
+/*----------------------------------------------------------------------------+
+| CODE section
++----------------------------------------------------------------------------*/
+
+BEGIN_CODE
+
+        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 is needed after doing I/O. We do it by writing to a non-existent port.
++----------------------------------------------------------------------------*/
+SYM(delay):
+	outb	al, $0xED	# about 1uS delay
+	ret
+
+/*-------------------------------------------------------------------------+
+|         Function: _load_segments
+|      Description: Load board segment registers with apropriate values + enable
+	            A20 line + reprogram PIC.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+        PUBLIC (_load_segments)
+SYM (_load_segments):
+	
+	LOAD_SEGMENTS(RESET_SS, ss)
+	LOAD_SEGMENTS(RESET_DS, ds)
+	LOAD_SEGMENTS(RESET_ES, es)
+	LOAD_SEGMENTS(RESET_FS, fs)
+	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
+	| the intel-reserved hardware interrupts, at int 0x20-0x2F. There they
+	| won't mess up anything. Sadly IBM really messed this up with the
+	| original PC, and they haven't been able to rectify it afterwards. Thus
+	| the bios puts interrupts at 0x08-0x0f, which is used for the internal
+	| hardware interrupts as well. We just have to reprogram the 8259's, and
+	| it isn't fun.
+	+---------------------------------------------------------------------*/
+
+	movb	$0x11, al		/* initialization sequence          */
+	outb	al, $0x20		/* send it to 8259A-1               */
+	call	SYM(delay)
+	outb	al, $0xA0		/* and to 8259A-2                   */
+	call	SYM(delay)
+	
+	movb	$0x20, al		/* start of hardware int's (0x20)   */
+	outb	al, $0x21
+	call	SYM(delay)
+	movb	$0x28, al		/* start of hardware int's 2 (0x28) */
+	outb	al, $0xA1
+	call	SYM(delay)
+	
+	movb	$0x04, al		/* 8259-1 is master                 */
+	outb	al, $0x21
+	call	SYM(delay)
+	movb	$0x02, al		/* 8259-2 is slave                  */
+	outb	al, $0xA1
+	call	SYM(delay)
+	
+	movb	$0x01, al		/* 8086 mode for both               */
+	outb	al, $0x21
+	call	SYM(delay)
+	outb	al, $0xA1
+	call	SYM(delay)
+	
+	movb	$0xFF, al		/* mask off all interrupts for now  */
+	outb	al, $0xA1
+	call	SYM(delay)
+	movb	$0xFB, al		/* mask all irq's but irq2 which    */
+	outb	al, $0x21		/* is cascaded                      */
+	call	SYM(delay)
+
+	jmp	SYM (_establish_stack)	# return to the bsp entry code
+
+/*-------------------------------------------------------------------------+
+|         Function: _return_to_monitor
+|      Description: Return to board's monitor (we have none so simply restart).
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+        PUBLIC (_return_to_monitor)
+SYM (_return_to_monitor):
+
+	call	SYM (Timer_exit)
+	call	SYM (Clock_exit)
+	jmp	SYM (start)
+
+END_CODE
+
+/*----------------------------------------------------------------------------+
+| DATA section
++----------------------------------------------------------------------------*/
+
+BEGIN_DATA
+
+        PUBLIC (_Do_Load_IDT)
+SYM (_Do_Load_IDT):
+       .byte 1	# load RTEMS own Interrupt Descriptor Table
+
+        PUBLIC (_Do_Load_GDT)
+SYM (_Do_Load_GDT):
+       .byte 0	# use the Global Descriptor Table that is already defined
+
+END_DATA
+
+END
Index: c/src/lib/libbsp/i386/pc386/startup/linkcmds
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/linkcmds	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/linkcmds	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,62 @@
+/*-------------------------------------------------------------------------+
+| linkcmds v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains directives for the GNU linker which are specific to the
+| PC386 bsp.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   linkcmds,v 1.3 1995/12/19 20:06:58 joel Exp - FORCE CPU386 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+SECTIONS
+{
+  .text :
+  {
+    _text_start = . ;
+    *(.text)
+    _etext = ALIGN( 0x10 ) ;
+  }
+  .rodata ADDR( .text ) + SIZEOF( .text ):
+  {
+    _rodata_start = . ;
+    *(.rodata)
+    _erodata = ALIGN( 0x10 ) ;
+  }
+  .data ADDR( .rodata ) + SIZEOF( .rodata ):
+  {
+    _data_start = . ;
+    *(.data)
+    _edata = ALIGN( 0x10 ) ;
+  }
+  .bss ADDR( .data ) + SIZEOF( .data ):
+  {
+    _bss_start = . ;
+    *(.bss)
+    *(COMMON)
+    _end = . ;
+    __end = . ;
+  }
+}
Index: c/src/lib/libbsp/i386/pc386/startup/sbrk.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/startup/sbrk.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/startup/sbrk.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,50 @@
+/*-------------------------------------------------------------------------+
+| sbrk.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| If the BSP wants to dynamically allocate the memory for the C Library heap
+| (malloc) and/or be able to extend the heap, then this routine must be
+| functional. RTEMS newlib suppport has an implementation of malloc using
+| RTEMS regions => the user can do mallocs.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is based on:
+|   sbrk.c,v 1.2 1995/12/19 20:07:38 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <errno.h>
+#include <sys/types.h>
+
+/*-------------------------------------------------------------------------+
+|         Function: sbrk
+|      Description: Stub for sbrk. 
+| Global Variables: None.
+|        Arguments: Not relevant.
+|          Returns: Not relevant. 
++--------------------------------------------------------------------------*/
+void *sbrk(size_t incr)
+{
+  errno = EINVAL;
+  return (void *)NULL;
+} /* sbrk */
Index: c/src/lib/libbsp/i386/pc386/timer/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/timer/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/timer/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,58 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+PGM=${ARCH}/timer.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=timer
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=${ARCH}/%.o)
+
+H_FILES=
+
+# Assembly source names, if any, go here -- minus the .s
+S_PIECES=timerisr
+S_FILES=$(S_PIECES:%=%.s)
+S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
+
+SRCS=$(C_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+${PGM}: ${SRCS} ${OBJS}
+	$(make-rel)
+
+all:	${ARCH} $(SRCS) $(PGM)
+
+# the .rel file built here will be put into libbsp.a by ../wrapup/Makefile
+install:  all
Index: c/src/lib/libbsp/i386/pc386/timer/timer.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/timer/timer.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/timer/timer.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,256 @@
+/*-------------------------------------------------------------------------+
+| timer.c v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the PC386 timer package.
++--------------------------------------------------------------------------+
+| NOTE: It is important that the timer start/stop overhead be determined
+|       when porting or modifying this code.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is base on:
+|   timer.c,v 1.7 1995/12/19 20:07:43 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include <stdlib.h>
+
+#include <bsp.h>
+#include <irq.h>
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define TIMER_IRQ     0x00           /* Timer IRQ.                            */
+#define AVG_OVERHEAD  0              /* 0.1 microseconds to start/stop timer. */
+#define LEAST_VALID   1              /* Don't trust a value lower than this.  */
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+volatile rtems_unsigned32 Ttimer_val;
+         rtems_boolean    Timer_driver_Find_average_overhead = TRUE;
+
+/*-------------------------------------------------------------------------+
+| Pentium optimized timer handling.
++--------------------------------------------------------------------------*/
+#if defined(pentium)
+
+/*-------------------------------------------------------------------------+
+|         Function: rdtsc
+|      Description: Read the value of PENTIUM on-chip cycle counter.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Value of PENTIUM on-chip cycle counter. 
++--------------------------------------------------------------------------*/
+static inline unsigned long long
+rdtsc(void)
+{
+  /* Return the value of the on-chip cycle counter. */
+  unsigned long long result;
+  asm volatile(".byte 0x0F, 0x31" : "=A" (result));
+  return result;
+} /* rdtsc */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Timer_exit
+|      Description: Timer cleanup routine at RTEMS exit. NOTE: This routine is
+|                   not really necessary, since there will be a reset at exit.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Timer_exit(void)
+{
+  PC386_disableIrq(TIMER_IRQ);
+} /* Timer_exit */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Timer_initialize
+|      Description: Timer initialization routine.
+| Global Variables: Ttimer_val.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Timer_initialize(void)
+{
+  static rtems_boolean First = TRUE;
+
+  if (First)
+  {
+    First = FALSE;
+
+    atexit(Timer_exit); /* Try not to hose the system at exit. */
+    PC386_enableIrq(TIMER_IRQ);
+                  /* Disable the programmable timer so ticks don't interfere. */
+  }
+  Ttimer_val = rdtsc(); /* read starting time */
+} /* Timer_initialize */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Read_timer
+|      Description: Read hardware timer value.
+| Global Variables: Ttimer_val, Timer_driver_Find_average_overhead.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+rtems_unsigned32
+Read_timer(void)
+{
+  register rtems_unsigned32 total;
+
+  total =  (rtems_unsigned32)(rdtsc() - Ttimer_val);
+
+  if (Timer_driver_Find_average_overhead)
+    return total;
+  else if (total < LEAST_VALID)
+    return 0; /* below timer resolution */
+  else
+    return (total - AVG_OVERHEAD);
+} /* Read_timer */
+
+#else /* pentium */
+
+/*-------------------------------------------------------------------------+
+| Non-Pentium timer handling.
++--------------------------------------------------------------------------*/
+#define US_PER_ISR   250  /* Number of micro-seconds per timer interruption */
+
+/*-------------------------------------------------------------------------+
+| External Prototypes
++--------------------------------------------------------------------------*/
+extern rtems_isr timerisr(rtems_vector_number);
+       /* timer (int 08h) Interrupt Service Routine (defined in 'timerisr.s') */
+
+/*-------------------------------------------------------------------------+
+|         Function: Timer_exit
+|      Description: Timer cleanup routine at RTEMS exit. NOTE: This routine is
+|                   not really necessary, since there will be a reset at exit.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Timer_exit(void)
+{
+  /* reset timer mode to standard (DOS) value */
+  outport_byte(TIMER_MODE, TIMER_SEL0|TIMER_16BIT|TIMER_RATEGEN);
+  outport_byte(TIMER_CNTR0, 0);
+  outport_byte(TIMER_CNTR0, 0);
+} /* Timer_exit */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Timer_initialize
+|      Description: Timer initialization routine.
+| Global Variables: Ttimer_val.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Timer_initialize(void)
+{
+  static rtems_boolean First = TRUE;
+
+  if (First)
+  {
+    First = FALSE;
+
+    atexit(Timer_exit); /* Try not to hose the system at exit. */
+
+    /* install a raw interrupt handler for timer */
+    PC386_installRawIrqHandler(TIMER_IRQ, timerisr);
+
+    /* load timer for US_PER_ISR microsecond period */
+    outport_byte(TIMER_MODE, TIMER_SEL0|TIMER_16BIT|TIMER_RATEGEN);
+    outport_byte(TIMER_CNTR0, US_TO_TICK(US_PER_ISR) >> 0 & 0xff);
+    outport_byte(TIMER_CNTR0, US_TO_TICK(US_PER_ISR) >> 8 & 0xff);
+  }
+  /* wait for ISR to be called at least once */
+  Ttimer_val = 0;
+  while (Ttimer_val == 0)
+    continue;
+  Ttimer_val = 0;
+} /* Timer_initialize */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Read_timer
+|      Description: Read hardware timer value.
+| Global Variables: Ttimer_val, Timer_driver_Find_average_overhead.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+rtems_unsigned32
+Read_timer(void)
+{
+  register rtems_unsigned32 total, clicks;
+  register rtems_unsigned8  lsb, msb;
+
+  outport_byte(TIMER_MODE, TIMER_SEL0|TIMER_LATCH);
+  inport_byte(TIMER_CNTR0, lsb);
+  inport_byte(TIMER_CNTR0, msb);
+  clicks = (msb << 8) | lsb;
+  total  = (Ttimer_val * US_PER_ISR) + (US_PER_ISR - TICK_TO_US(clicks));
+
+  if (Timer_driver_Find_average_overhead)
+    return total;
+  else if (total < LEAST_VALID)
+    return 0; /* below timer resolution */
+  else
+    return (total - AVG_OVERHEAD);
+}
+
+#endif /* pentium */
+
+
+/*-------------------------------------------------------------------------+
+|         Function: Empty_function
+|      Description: Empty function used in time tests.
+| Global Variables: None.
+|        Arguments: None.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+rtems_status_code Empty_function(void)
+{
+  return RTEMS_SUCCESSFUL;
+} /* Empty function */
+ 
+
+/*-------------------------------------------------------------------------+
+|         Function: Set_find_average_overhead
+|      Description: Set internal Timer_driver_Find_average_overhead flag value.
+| Global Variables: Timer_driver_Find_average_overhead.
+|        Arguments: find_flag - new value of the flag.
+|          Returns: Nothing. 
++--------------------------------------------------------------------------*/
+void
+Set_find_average_overhead(rtems_boolean find_flag)
+{
+  Timer_driver_Find_average_overhead = find_flag;
+} /* Set_find_average_overhead */
Index: c/src/lib/libbsp/i386/pc386/timer/timerisr.s
===================================================================
--- c/src/lib/libbsp/i386/pc386/timer/timerisr.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/timer/timerisr.s	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,59 @@
+/*-------------------------------------------------------------------------+
+| timerisr.s v1.1 - PC386 BSP - 1997/08/07
++--------------------------------------------------------------------------+
+| This file contains the PC386 timer interrupt handler.
++--------------------------------------------------------------------------+
+| (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.
++--------------------------------------------------------------------------+
+| This code is base on:
+|   timerisr.s,v 1.5 1995/12/19 20:07:45 joel Exp - go32 BSP
+| With the following copyright notice:
+| **************************************************************************
+| * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.                      *
+| * On-Line Applications Research Corporation (OAR).                       *
+| * All rights assigned to U.S. Government, 1994.                          *
+| *                                                                        *
+| * This material may be reproduced by or for the U.S. Government pursuant *
+| * to the copyright license under the clause at DFARS 252.227-7013.  This *
+| * notice must appear in all copies of this file and its derivatives.     *
+| **************************************************************************
++--------------------------------------------------------------------------*/
+
+
+#include "asm.h"
+
+BEGIN_CODE
+
+	EXTERN(Ttimer_val)
+
+/*-------------------------------------------------------------------------+
+|         Function: rtems_isr timerisr(rtems_vector_number);
+|      Description: ISR for the timer. The timer is set up to generate an
+|                   interrupt at maximum intervals.
+| Global Variables: None.
+|        Arguments: standard - see RTEMS documentation.
+|          Returns: standard return value - see RTEMS documentation. 
++--------------------------------------------------------------------------*/
+	PUBLIC(timerisr)
+SYM (timerisr): 
+	incl	Ttimer_val	# another tick
+	pushl	eax
+	movb	$0x20, al
+	outb	al, $0x20	# signal generic End Of Interrupt (EOI) to PIC
+	popl	eax
+	iret
+
+END_CODE
+
+END
+
Index: c/src/lib/libbsp/i386/pc386/times_i486dx
===================================================================
--- c/src/lib/libbsp/i386/pc386/times_i486dx	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/times_i486dx	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,191 @@
+#
+#  Timing Test Suite Results for the go32 BSP using an i486DX
+#
+#  times_i486dx,v 1.4 1996/07/02 18:14:27 joel Exp
+#
+
+Board:                PC/AT clone
+CPU:                  Intel i486DX
+Clock Speed:          33 Mhz
+Memory Configuration: DRAM w/256K cache
+Wait States:          unknown
+
+Times Reported in:    microseconds
+Timer Source:         i8254
+
+Column A:             3.5.1 pre-release
+Column B:             3.5.17 pre-release
+
+#                          DESCRIPTION                                 A    B
+== =================================================================  ==== ====
+ 1 rtems_semaphore_create                                               57   66
+   rtems_semaphore_delete                                               59   61
+   rtems_semaphore_obtain: available                                     9    7
+   rtems_semaphore_obtain: not available -- NO_WAIT                      8    7
+   rtems_semaphore_release: no waiting tasks                             9    8
+
+ 2 rtems_semaphore_obtain: not available -- caller blocks               39   37
+
+ 3 rtems_semaphore_release: task readied -- preempts caller             25   24
+
+ 4 rtems_task_restart: blocked task -- preempts caller                 124  102
+   rtems_task_restart: ready task -- preempts caller                    55  111
+   rtems_semaphore_release: task readied -- returns to caller           16   15
+   rtems_task_create                                                    31   30
+   rtems_task_start                                                     19   18
+   rtems_task_restart: suspended task -- returns to caller              20   19
+   rtems_task_delete: suspended task                                    28   26
+   rtems_task_restart: ready task -- returns to caller                  20   19
+   rtems_task_restart: blocked task -- returns to caller                28   26
+   rtems_task_delete: blocked task                                      34   28
+
+ 5 rtems_task_suspend: calling task                                     26   23
+   rtems_task_resume: task readied -- preempts caller                   17   15
+
+ 6 rtems_task_restart: calling task                                     22   19
+   rtems_task_suspend: returns to caller                                10    8
+   rtems_task_resume: task readied -- returns to caller                 10    8
+   rtems_task_delete: ready task                                        34   33
+
+ 7 rtems_task_restart: suspended task -- preempts caller                37   34
+
+ 8 rtems_task_set_priority: obtain current priority                      7    5
+   rtems_task_set_priority: returns to caller                           13   12
+   rtems_task_mode: obtain current mode                                  3    3
+   rtems_task_mode: no reschedule                                        4    4
+   rtems_task_mode: reschedule -- returns to caller                     20   17
+   rtems_task_mode: reschedule -- preempts caller                       39   37
+   rtems_task_set_note                                                   7    5
+   rtems_task_get_note                                                   7    5
+   rtems_clock_set                                                      17   16
+   rtems_clock_get                                                       2    1
+
+ 9 rtems_message_queue_create                                          117  113
+   rtems_message_queue_send: no waiting tasks                           22   19
+   rtems_message_queue_urgent: no waiting tasks                         22   19
+   rtems_message_queue_receive: available                               18   16
+   rtems_message_queue_flush: no messages flushed                       15   14
+   rtems_message_queue_flush: messages flushed                          17   17
+   rtems_message_queue_delete                                           63   63
+
+10 rtems_message_queue_receive: not available -- NO_WAIT                10    8
+   rtems_message_queue_receive: not available -- caller blocks          42   40
+
+11 rtems_message_queue_send: task readied -- preempts caller            38   37
+
+12 rtems_message_queue_send: task readied -- returns to caller          27   24
+
+13 rtems_message_queue_urgent: task readied -- preempts caller          38   36
+
+14 rtems_message_queue_urgent: task readied -- returns to caller        26   24
+
+15 rtems_event_receive: obtain current events                            0    0
+   rtems_event_receive: not available -- NO_WAIT                         6    5
+   rtems_event_receive: not available -- caller blocks                  34   33
+   rtems_event_send: no task readied                                     6    5
+   rtems_event_receive: available                                       21   19
+   rtems_event_send: task readied -- returns to caller                  19   15
+
+16 rtems_event_send: task readied -- preempts caller                    26   24
+
+17 rtems_task_set_priority: preempts caller                             36   33
+
+18 rtems_task_delete: calling task                                      51   52
+
+19 rtems_signal_catch                                                   17   18
+   rtems_signal_send: returns to caller                                 38   39
+   rtems_signal_send: signal to self                                    46   62
+   exit ASR overhead: returns to calling task                           20   25
+   exit ASR overhead: returns to preempting task                        29   29
+
+20 rtems_partition_create                                               65   67
+   rtems_region_create                                                  59   54
+   rtems_partition_get_buffer: available                                39   35
+   rtems_partition_get_buffer: not available                            18   16
+   rtems_partition_return_buffer                                        36   30
+   rtems_partition_delete                                               32   30
+   rtems_region_get_segment: available                                  22   21
+   rtems_region_get_segment: not available -- NO_WAIT                   29   25
+   rtems_region_return_segment: no waiting tasks                        24   22
+   rtems_region_get_segment: not available -- caller blocks             83   81
+   rtems_region_return_segment: task readied -- preempts caller         85   84
+   rtems_region_return_segment: task readied -- returns to caller       39   41
+   rtems_region_delete                                                  30   30
+   rtems_io_initialize                                                   1    1
+   rtems_io_open                                                         0    0
+   rtems_io_close                                                        0    0
+   rtems_io_read                                                         0    0
+   rtems_io_write                                                        0    0
+   rtems_io_control                                                      0    1
+
+21 rtems_task_ident                                                    116  114
+   rtems_message_queue_ident                                           113  111
+   rtems_semaphore_ident                                               122  120
+   rtems_partition_ident                                               113  110
+   rtems_region_ident                                                  115  111
+   rtems_port_ident                                                    113  109
+   rtems_timer_ident                                                   113  109
+   rtems_rate_monotonic_ident                                          113  111
+
+22 rtems_message_queue_broadcast: task readied -- returns to caller     82   85
+   rtems_message_queue_broadcast: no waiting tasks                      11    9
+   rtems_message_queue_broadcast: task readied -- preempts caller       51   56
+
+23 rtems_timer_create                                                    8    7
+   rtems_timer_fire_after: inactive                                     14   12
+   rtems_timer_fire_after: active                                       13   12
+   rtems_timer_cancel: active                                            8    7
+   rtems_timer_cancel: inactive                                          7    6
+   rtems_timer_reset: inactive                                          11   10
+   rtems_timer_reset: active                                            11   11
+   rtems_timer_fire_when: inactive                                      17   16
+   rtems_timer_fire_when: active                                        17   17
+   rtems_timer_delete: active                                           10    9
+   rtems_timer_delete: inactive                                          9    8
+   rtems_task_wake_when                                                 36   34
+
+24 rtems_task_wake_after: yield -- returns to caller                     5    3
+   rtems_task_wake_after: yields -- preempts caller                     22   19
+
+25 rtems_clock_tick                                                     31   31
+
+26 _ISR_Disable                                                         11   12
+   _ISR_Flash                                                            9    9
+   _ISR_Enable                                                          31   67
+   _Thread_Disable_dispatch                                             11   10
+   _Thread_Enable_dispatch                                              18   18
+   _Thread_Set_state                                                    20   22
+   _Thread_Disptach (NO FP)                                             37   41
+   context switch: no floating point contexts                           29   26
+   context switch: self                                                 14   10
+   context switch: to another task                                      12   12
+   context switch: restore 1st FP task                                  54   54
+   fp context switch: save idle, restore idle                           47   46
+   fp context switch: save idle, restore initialized                    25   25
+   fp context switch: save initialized, restore initialized             24   25
+   _Thread_Resume                                                       23   24
+   _Thread_Unblock                                                      14   14
+   _Thread_Ready                                                        16   24
+   _Thread_Get                                                           2    2
+   _Semaphore_Get                                                        1    1
+   _Thread_Get: invalid id                                               0    0
+
+27 interrupt entry overhead: returns to interrupted task                25   23
+   interrupt exit overhead: returns to interrupted task                 14   15
+   interrupt entry overhead: returns to nested interrupt                12   12
+   interrupt exit overhead: returns to nested interrupt                 14   14
+   interrupt entry overhead: returns to preempting task                 14   16
+   interrupt exit overhead: returns to preempting task                  42   38
+
+28 rtems_port_create                                                    43   42
+   rtems_port_external_to_internal                                       6    4
+   rtems_port_internal_to_external                                       6    4
+   rtems_port_delete                                                    39   33
+
+29 rtems_rate_monotonic_create                                          48   42
+   rtems_rate_monotonic_period: initiate period -- returns to caller    61   65
+   rtems_rate_monotonic_period: obtain status                           23   21
+   rtems_rate_monotonic_cancel                                          38   35
+   rtems_rate_monotonic_delete: inactive                                32   32
+   rtems_rate_monotonic_delete: active                                  22   22
+   rtems_rate_monotonic_period: conclude periods -- caller blocks       24   19
Index: c/src/lib/libbsp/i386/pc386/times_p5
===================================================================
--- c/src/lib/libbsp/i386/pc386/times_p5	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/times_p5	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,196 @@
+#
+#  Timing Test Suite Results for the go32 BSP using a Pentium
+#
+#  times_p5,v 1.3 1995/12/19 20:07:20 joel Exp
+#
+
+NOTE:  To obtain the execution time in microseconds, divide the number of
+       cycles by the clock speed.  For example, if rtems_semaphore create 
+       is reported to be 1164 cycles, then at 66 Mhz it takes 17.64 
+       microseconds or 8.75 microseconds at 133 Mhz.
+
+Board:                PC/AT clone
+CPU:                  Intel Pentium
+Clock Speed:          66 Mhz
+Memory Configuration: DRAM w/512 Kb cache
+Wait States:          unknown
+
+Times Reported in:    cycles
+Timer Source:         on-CPU cycle counter
+
+Column A:             3.5.1 pre-release
+Column Y:             unused
+
+#                          DESCRIPTION                                 A    B
+== =================================================================  ==== ====
+ 1 rtems_semaphore_create                                             1164
+   rtems_semaphore_delete                                              976
+   rtems_semaphore_obtain: available                                   300
+   rtems_semaphore_obtain: not available -- NO_WAIT                    300
+   rtems_semaphore_release: no waiting tasks                           291
+
+ 2 rtems_semaphore_obtain: not available -- caller blocks             1182
+
+ 3 rtems_semaphore_release: task readied -- preempts caller            716
+
+ 4 rtems_task_restart: blocked task -- preempts caller                2130
+   rtems_task_restart: ready task -- preempts caller                  1861
+   rtems_semaphore_release: task readied -- returns to caller          491
+   rtems_task_create                                                  1017
+   rtems_task_start                                                    965
+   rtems_task_restart: suspended task -- returns to caller             816
+   rtems_task_delete: suspended task                                   926
+   rtems_task_restart: ready task -- returns to caller                 850
+   rtems_task_restart: blocked task -- returns to caller              1076
+   rtems_task_delete: blocked task                                     927
+
+ 5 rtems_task_suspend: calling task                                    714
+   rtems_task_resume: task readied -- preempts caller                  575
+
+ 6 rtems_task_restart: calling task                                    646
+   rtems_task_suspend: returns to caller                               309
+   rtems_task_resume: task readied -- returns to caller                320
+   rtems_task_delete: ready task                                       994
+
+ 7 rtems_task_restart: suspended task -- preempts caller              1025
+
+ 8 rtems_task_set_priority: obtain current priority                    223
+   rtems_task_set_priority: returns to caller                          468
+   rtems_task_mode: obtain current mode                                 99
+   rtems_task_mode: no reschedule                                      114
+   rtems_task_mode: reschedule -- returns to caller                    264
+   rtems_task_mode: reschedule -- preempts caller                      836
+   rtems_task_set_note                                                 236
+   rtems_task_get_note                                                 232
+   rtems_clock_set                                                     569
+   rtems_clock_get                                                     107
+
+ 9 rtems_message_queue_create                                         3287
+   rtems_message_queue_send: no waiting tasks                          613
+   rtems_message_queue_urgent: no waiting tasks                        615
+   rtems_message_queue_receive: available                              534
+   rtems_message_queue_flush: no messages flushed                      252
+   rtems_message_queue_flush: messages flushed                         335
+   rtems_message_queue_delete                                         1195
+
+10 rtems_message_queue_receive: not available -- NO_WAIT               333
+   rtems_message_queue_receive: not available -- caller blocks        1194
+
+11 rtems_message_queue_send: task readied -- preempts caller           957
+
+12 rtems_message_queue_send: task readied -- returns to caller         700
+
+13 rtems_message_queue_urgent: task readied -- preempts caller        1261
+
+14 rtems_message_queue_urgent: task readied -- returns to caller       697
+
+15 rtems_event_receive: obtain current events                           27
+   rtems_event_receive: not available -- NO_WAIT                       226
+   rtems_event_receive: not available -- caller blocks                 888
+   rtems_event_send: no task readied                                   221
+   rtems_event_receive: available                                      393
+   rtems_event_send: task readied -- returns to caller                 496
+
+16 rtems_event_send: task readied -- preempts caller                   719
+
+17 rtems_task_set_priority: preempts caller                            959
+
+18 rtems_task_delete: calling task                                    1295
+
+19 rtems_signal_catch                                                  223
+   rtems_signal_send: returns to caller                                628
+   rtems_signal_send: signal to self                                   821
+   exit ASR overhead: returns to calling task                          401
+   exit ASR overhead: returns to preempting task                       482
+
+20 rtems_partition_create                                             1337
+   rtems_region_create                                                1031
+   rtems_partition_get_buffer: available                               680
+   rtems_partition_get_buffer: not available                           303
+   rtems_partition_return_buffer                                       617
+   rtems_partition_delete                                              523
+   rtems_region_get_segment: available                                 458
+   rtems_region_get_segment: not available -- NO_WAIT                  565
+   rtems_region_return_segment: no waiting tasks                       388
+   rtems_region_get_segment: not available -- caller blocks           1683
+   rtems_region_return_segment: task readied -- preempts caller       1476
+   rtems_region_return_segment: task readied -- returns to caller      818
+   rtems_region_delete                                                 477
+   rtems_io_initialize                                                  48
+   rtems_io_open                                                        22
+   rtems_io_close                                                       22
+   rtems_io_read                                                        22
+   rtems_io_write                                                       22
+   rtems_io_control                                                     23
+
+21 rtems_task_ident                                                   3381
+   rtems_message_queue_ident                                          3328
+   rtems_semaphore_ident                                              3593
+   rtems_partition_ident                                              3286
+   rtems_region_ident                                                 3343
+   rtems_port_ident                                                   3278
+   rtems_timer_ident                                                  3282
+   rtems_rate_monotonic_ident                                         3287
+
+22 rtems_message_queue_broadcast: task readied -- returns to caller   1322
+   rtems_message_queue_broadcast: no waiting tasks                     347
+   rtems_message_queue_broadcast: task readied -- preempts caller     1385
+
+23 rtems_timer_create                                                  306
+   rtems_timer_fire_after: inactive                                    475
+   rtems_timer_fire_after: active                                      475
+   rtems_timer_cancel: active                                          277
+   rtems_timer_cancel: inactive                                        251
+   rtems_timer_reset: inactive                                         391
+   rtems_timer_reset: active                                           465
+   rtems_timer_fire_when: inactive                                     577
+   rtems_timer_fire_when: active                                       578
+   rtems_timer_delete: active                                          377
+   rtems_timer_delete: inactive                                        350
+   rtems_task_wake_when                                               1080
+
+24 rtems_task_wake_after: yield -- returns to caller                   159
+   rtems_task_wake_after: yields -- preempts caller                    574
+
+25 rtems_clock_tick                                                    505
+
+26 _ISR_Disable                                                         33
+   _ISR_Flash                                                           33
+   _ISR_Enable                                                          26
+   _Thread_Disable_dispatch                                             36
+   _Thread_Enable_dispatch                                             240
+   _Thread_Set_state                                                   315
+   _Thread_Disptach (NO FP)                                            623
+   context switch: no floating point contexts                          594
+   context switch: self                                                 89
+   context switch: to another task                                     122
+   context switch: restore 1st FP task                                1043
+   fp context switch: save idle, restore idle                          978
+   fp context switch: save idle, restore initialized                   390
+   fp context switch: save initialized, restore initialized            392
+   _Thread_Resume                                                      238
+   _Thread_Unblock                                                     171
+   _Thread_Ready                                                       176
+   _Thread_Get                                                          71
+   _Semaphore_Get                                                       61
+   _Thread_Get: invalid id                                              10
+
+27 interrupt entry overhead: returns to interrupted task               391
+   interrupt exit overhead: returns to interrupted task                110
+   interrupt entry overhead: returns to nested interrupt               167
+   interrupt exit overhead: returns to nested interrupt                120
+   interrupt entry overhead: returns to preempting task                193
+   interrupt exit overhead: returns to preempting task                 961
+
+28 rtems_port_create                                                   668
+   rtems_port_external_to_internal                                     215
+   rtems_port_internal_to_external                                     211
+   rtems_port_delete                                                   491
+
+29 rtems_rate_monotonic_create                                         823
+   rtems_rate_monotonic_period: initiate period -- returns to caller  1094
+   rtems_rate_monotonic_period: obtain status                          345
+   rtems_rate_monotonic_cancel                                         602
+   rtems_rate_monotonic_delete: inactive                               553
+   rtems_rate_monotonic_delete: active                                 528
+   rtems_rate_monotonic_period: conclude periods -- caller blocks      672
Index: c/src/lib/libbsp/i386/pc386/tools/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/tools/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/tools/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,63 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+exec_prefix = @exec_prefix@
+bindir = @bindir@
+libdir = @libdir@
+includedir = @includedir@
+manext = 1
+mandir = @mandir@/man$(manext)
+
+
+VPATH=@srcdir@
+
+
+# we use host compiler in this directory
+USE_HOST_COMPILER=yes
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=bin2boot
+C_FILES=$(C_PIECES:%=%.c)
+C_O_FILES=$(C_PIECES:%=$(ARCH)/%.o)
+
+H_FILES=
+
+SRCS=$(C_FILES) $(CC_FILES) $(H_FILES)
+OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
+
+PGMS=$(ARCH)/bin2boot
+
+include $(RTEMS_CUSTOM)
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS += $(HOST_ARCH)
+CLOBBER_ADDITIONS +=
+
+all:	$(ARCH) $(SRCS) $(PGMS)
+	$(INSTALL_VARIANT) -m 555 $(PGMS) ${PROJECT_RELEASE}/build-tools
+	cd ${PROJECT_RELEASE}/build-tools/diskboot.exe ; \
+	  uudecode < $(srcdir)/diskboot.uue
Index: c/src/lib/libbsp/i386/pc386/tools/bin2boot.c
===================================================================
--- c/src/lib/libbsp/i386/pc386/tools/bin2boot.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/tools/bin2boot.c	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,239 @@
+/*-------------------------------------------------------------------------+
+| 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.
++--------------------------------------------------------------------------*/
+
+
+#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 */
Index: c/src/lib/libbsp/i386/pc386/wrapup/Makefile.in
===================================================================
--- c/src/lib/libbsp/i386/pc386/wrapup/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
+++ c/src/lib/libbsp/i386/pc386/wrapup/Makefile.in	(revision 7150f00f5be87fa8e37f7d00fbbef35645081138)
@@ -0,0 +1,48 @@
+#
+#  $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+VPATH=@srcdir@
+
+BSP_PIECES=startup clock console timer
+GENERIC_PIECES=
+
+# bummer; have to use $foreach since % pattern subst rules only replace 1x
+OBJS=$(foreach piece, $(BSP_PIECES), ../$(piece)/$(ARCH)/$(piece).rel) \
+     $(foreach piece, $(GENERIC_PIECES), ../../../$(piece)/$(ARCH)/$(piece).rel)
+LIB=$(ARCH)/libbsp.a
+
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/lib.cfg
+
+#
+# (OPTIONAL) Add local stuff here using +=
+#
+
+DEFINES  +=
+CPPFLAGS +=
+CFLAGS   +=
+
+LD_PATHS  +=
+LD_LIBS   +=
+LDFLAGS   +=
+
+#
+# Add your list of files to delete here.  The config files
+#  already know how to delete some stuff, so you may want
+#  to just run 'make clean' first to see what gets missed.
+#  'make clobber' already includes 'make clean'
+#
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+$(LIB): ${OBJS}
+	$(make-library)
+
+all:	${ARCH} $(SRCS) $(LIB)
+	$(INSTALL_VARIANT) -m 644 $(LIB) ${PROJECT_RELEASE}/lib
+
