summaryrefslogtreecommitdiffstats
path: root/c/src/lib/libbsp/powerpc/ppcn_60x
diff options
context:
space:
mode:
authorJoel Sherrill <joel.sherrill@OARcorp.com>1999-02-18 16:48:14 +0000
committerJoel Sherrill <joel.sherrill@OARcorp.com>1999-02-18 16:48:14 +0000
commit0c04c377bc8ac177d28bd0e0096d7c6940d33cd4 (patch)
treeba3062eb819e89de2eee14397ffe61b202ad10de /c/src/lib/libbsp/powerpc/ppcn_60x
parent./clock/Makefile.in,v (diff)
downloadrtems-0c04c377bc8ac177d28bd0e0096d7c6940d33cd4.tar.bz2
./clock/Makefile.in,v
./clock/clock.c,v ./console/Makefile.in,v ./console/config.c,v ./console/console.c,v ./console/console.h,v ./console/debugio.c,v ./console/i8042.c,v ./console/i8042_p.h,v ./console/i8042vga.c,v ./console/i8042vga.h,v ./console/ns16550.c,v ./console/ns16550.h,v ./console/ns16550_p.h,v ./console/ns16550cfg.c,v ./console/ns16550cfg.h,v ./console/vga.c,v ./console/vga_p.h,v ./console/z85c30.c,v ./console/z85c30.h,v ./console/z85c30_p.h,v ./console/z85c30cfg.c,v ./console/z85c30cfg.h,v ./include/Makefile.in,v ./include/bsp.h,v ./include/chain.h,v ./include/coverhd.h,v ./include/extisrdrv.h,v ./include/nvram.h,v ./include/pci.h,v ./include/tod.h,v ./network/Makefile.in,v ./network/amd79c970.c,v ./network/amd79c970.h,v ./nvram/Makefile.in,v ./nvram/ds1385.h,v ./nvram/mk48t18.h,v ./nvram/nvram.c,v ./nvram/prepnvr.h,v ./nvram/stk11c68.h,v ./pci/Makefile.in,v ./pci/pci.c,v ./start/Makefile.in,v ./start/start.s,v ./startup/Makefile.in,v ./startup/bspclean.c,v ./startup/bspstart.c,v ./startup/bsptrap.s,v ./startup/device-tree,v ./startup/genpvec.c,v ./startup/linkcmds,v ./startup/rtems-ctor.cc,v ./startup/sbrk.c,v ./startup/setvec.c,v ./startup/spurious.c,v ./startup/swap.c,v ./timer/Makefile.in,v ./timer/timer.c,v ./tod/Makefile.in,v ./tod/cmos.h,v ./tod/tod.c,v ./universe/Makefile.in,v ./universe/universe.c,v ./vectors/Makefile.in,v ./vectors/README,v ./vectors/align_h.s,v ./vectors/vectors.s,v ./wrapup/Makefile.in,v ./Makefile.in,v ./README,v ./STATUS,v ./bsp_specs,v
Diffstat (limited to 'c/src/lib/libbsp/powerpc/ppcn_60x')
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/Makefile.in25
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/README48
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/STATUS8
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/bsp_specs23
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/clock/Makefile.in59
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/clock/clock.c241
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/Makefile.in54
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/console.c358
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/console.h67
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042.c1073
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042_p.h196
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.c46
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.h34
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.c632
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.h40
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550_p.h196
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.c53
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.h55
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/vga.c368
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/vga_p.h70
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.c917
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.h52
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30_p.h385
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.c96
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.h64
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/Makefile.in36
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/bsp.h465
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/chain.h362
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/coverhd.h119
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/extisrdrv.h41
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/nvram.h60
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/pci.h322
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/include/tod.h38
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/network/Makefile.in54
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.c1010
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.h426
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/Makefile.in56
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/ds1385.h39
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/mk48t18.h87
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/nvram.c515
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/prepnvr.h127
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/nvram/stk11c68.h46
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/pci/Makefile.in56
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/pci/pci.c342
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/start/Makefile.in54
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/start/start.S153
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/Makefile.in62
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspclean.c30
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspstart.c305
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/bsptrap.S25
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/genpvec.c355
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/linkcmds173
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/rtems-ctor.cc124
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/setvec.c55
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/spurious.c202
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/startup/swap.c64
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/timer/Makefile.in59
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/timer/timer.c82
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/tod/Makefile.in56
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/tod/cmos.h95
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/tod/tod.c617
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/universe/Makefile.in54
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/universe/universe.c449
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/vectors/Makefile.in59
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/vectors/README25
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/vectors/align_h.S434
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/vectors/vectors.S297
-rw-r--r--c/src/lib/libbsp/powerpc/ppcn_60x/wrapup/Makefile.in59
68 files changed, 13249 insertions, 0 deletions
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/Makefile.in
new file mode 100644
index 0000000000..ff468879d0
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/Makefile.in
@@ -0,0 +1,25 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/directory.cfg
+
+SRCS=README
+
+# We only build the network device driver if HAS_NETWORK was defined
+# NETWORK_DRIVER_yes_V = network
+# NETWORK_DRIVER = $(NETWORK_DRIVER_$(HAS_NETWORK)_V)
+
+all: $(SRCS)
+
+# wrapup is the one that actually builds and installs the library
+# from the individual .rel files built in other directories
+SUB_DIRS=include clock console startup start timer tod \
+ $(NETWORK_DRIVER) universe pci nvram vectors wrapup
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/README b/c/src/lib/libbsp/powerpc/ppcn_60x/README
new file mode 100644
index 0000000000..197c652369
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/README
@@ -0,0 +1,48 @@
+#
+# $Id$
+#
+
+BSP NAME: psim
+BOARD: PowerPC Simulator
+BUS: N/A
+CPU FAMILY: ppc
+CPU: PowerPC 603, 603e, 604
+COPROCESSORS: N/A
+MODE: 32 bit mode
+
+DEBUG MONITOR: BUG mode (emulates Motorola debug monitor)
+
+PERIPHERALS
+===========
+TIMERS: PPC internal Timebase register
+ RESOLUTION: ???
+SERIAL PORTS: simulated via bug
+REAL-TIME CLOCK: PPC internal Decrementer register
+DMA: none
+VIDEO: none
+SCSI: none
+NETWORKING: none
+
+DRIVER INFORMATION
+==================
+CLOCK DRIVER: PPC internal
+IOSUPP DRIVER: N/A
+SHMSUPP: N/A
+TIMER DRIVER: PPC internal
+TTY DRIVER: PPC internal
+
+STDIO
+=====
+PORT: Console port 0
+ELECTRICAL: na
+BAUD: na
+BITS PER CHARACTER: na
+PARITY: na
+STOP BITS: na
+
+Notes
+=====
+
+Based on papyrus bsp which only really supports
+the PowerOpen ABI with an ELF assembler.
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/STATUS b/c/src/lib/libbsp/powerpc/ppcn_60x/STATUS
new file mode 100644
index 0000000000..cc05554441
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/STATUS
@@ -0,0 +1,8 @@
+#
+# $Id$
+#
+
+These are the notes made while updating this BSP to a more current
+RTEMS version.
+
+ + device-tree is psim specific and was removed
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/bsp_specs b/c/src/lib/libbsp/powerpc/ppcn_60x/bsp_specs
new file mode 100644
index 0000000000..ab5a8ddbeb
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/bsp_specs
@@ -0,0 +1,23 @@
+%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 \
+%{!qrtems_debug: -lrtemsall} %{qrtems_debug: -lrtemsall_g} \
+-lc -lgcc --end-group ecrtn%O%s \
+%{!qnolinkcmds: -T linkcmds%s}}
+
+*startfile:
+%{!qrtems: %(old_startfile)} %{qrtems: ecrti%O%s \
+%{!qrtems_debug: start.o%s} \
+%{qrtems_debug: start_g.o%s}}
+
+*link:
+%{!qrtems: %(old_link)} %{qrtems: -Qy -dp -Bstatic -T linkcmds%s -e _start -u __vectors}
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/clock/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/clock/Makefile.in
new file mode 100644
index 0000000000..7c2cfc0772
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/clock/Makefile.in
@@ -0,0 +1,59 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/clock.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=clock
+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=
+S_FILES=$(S_PIECES:%=%.s)
+S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
+
+SRCS=$(C_FILES) $(CC_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/clock/clock.c b/c/src/lib/libbsp/powerpc/ppcn_60x/clock/clock.c
new file mode 100644
index 0000000000..29ca97be32
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/clock/clock.c
@@ -0,0 +1,241 @@
+/*
+ * Clock Tick Device Driver
+ *
+ * This routine utilizes the Decrementer Register common to the PPC family.
+ *
+ * The tick frequency is directly programmed to the configured number of
+ * microseconds per tick.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#include <stdlib.h>
+
+#include <bsp.h>
+#include <rtems/libio.h>
+#include <assert.h>
+
+/*
+ * The Real Time Clock Counter Timer uses this trap type.
+ */
+
+#define CLOCK_VECTOR PPC_IRQ_DECREMENTER
+
+/*
+ * Clock ticks since initialization
+ */
+
+volatile rtems_unsigned32 Clock_driver_ticks;
+
+/*
+ * This is the value programmed into the count down timer.
+ */
+
+rtems_unsigned32 Clock_Decrementer_value;
+
+rtems_isr_entry Old_ticker;
+
+void Clock_exit( void );
+
+/*
+ * These are set by clock driver during its init
+ */
+
+rtems_device_major_number rtems_clock_major = ~0;
+rtems_device_minor_number rtems_clock_minor;
+
+#define PPC_Set_decrementer( _clicks ) \
+ do { \
+ asm volatile( "mtdec %0" : "=r" ((_clicks)) : "r" ((_clicks)) ); \
+ } while (0)
+
+
+/*
+ * Clock_isr
+ *
+ * This is the clock tick interrupt handler.
+ *
+ * Input parameters:
+ * vector - vector number
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ *
+ */
+rtems_isr Clock_isr(
+ rtems_vector_number vector,
+ CPU_Interrupt_frame *frame
+)
+{
+ /*
+ * Set the decrementer.
+ */
+
+ PPC_Set_decrementer( Clock_Decrementer_value );
+
+ /*
+ * The driver has seen another tick.
+ */
+
+ Clock_driver_ticks += 1;
+
+ /*
+ * Real Time Clock counter/timer is set to automatically reload.
+ */
+
+ rtems_clock_tick();
+}
+
+/*
+ * Install_clock
+ *
+ * This routine actually performs the hardware initialization for the clock.
+ *
+ * Input parameters:
+ * clock_isr - clock interrupt service routine entry point
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ *
+ */
+
+extern int CLOCK_SPEED;
+
+void Install_clock(
+ rtems_isr_entry clock_isr
+)
+{
+ Clock_driver_ticks = 0;
+
+ if ( BSP_Configuration.ticks_per_timeslice ) {
+ Old_ticker = (rtems_isr_entry) set_vector( clock_isr, CLOCK_VECTOR, 1 );
+
+ PPC_Set_decrementer( Clock_Decrementer_value );
+
+ atexit( Clock_exit );
+ }
+}
+
+/*
+ * Clock_exit
+ *
+ * This routine allows the clock driver to exit by masking the interrupt and
+ * disabling the clock's counter.
+ *
+ * Input parameters: NONE
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ *
+ */
+
+void Clock_exit( void )
+{
+ if ( BSP_Configuration.ticks_per_timeslice ) {
+
+ /* nothing to do */;
+
+ /* do not restore old vector */
+ }
+}
+
+/*
+ * Clock_initialize
+ *
+ * This routine initializes the clock driver.
+ *
+ * Input parameters:
+ * major - clock device major number
+ * minor - clock device minor number
+ * parg - pointer to optional device driver arguments
+ *
+ * Output parameters: NONE
+ *
+ * Return values:
+ * rtems_device_driver status code
+ */
+
+rtems_device_driver Clock_initialize(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void *pargp
+)
+{
+ Clock_Decrementer_value = (ulCpuBusClock/4000)*
+ (BSP_Configuration.microseconds_per_tick/1000);
+
+ Install_clock((rtems_isr_entry)Clock_isr);
+
+ /*
+ * make major/minor avail to others such as shared memory driver
+ */
+
+ rtems_clock_major = major;
+ rtems_clock_minor = minor;
+
+ return RTEMS_SUCCESSFUL;
+}
+
+/*
+ * Clock_control
+ *
+ * This routine is the clock device driver control entry point.
+ *
+ * Input parameters:
+ * major - clock device major number
+ * minor - clock device minor number
+ * parg - pointer to optional device driver arguments
+ *
+ * Output parameters: NONE
+ *
+ * Return values:
+ * rtems_device_driver status code
+ */
+
+rtems_device_driver Clock_control(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void *pargp
+)
+{
+ rtems_unsigned32 isrlevel;
+ rtems_libio_ioctl_args_t *args = pargp;
+
+ if (args == 0)
+ goto done;
+
+ /*
+ * 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', ' '))
+ {
+ Clock_isr( CLOCK_VECTOR, pargp );
+ }
+ else if (args->command == rtems_build_name('N', 'E', 'W', ' '))
+ {
+ rtems_interrupt_disable( isrlevel );
+ (void) set_vector( args->buffer, CLOCK_VECTOR, 1 );
+ rtems_interrupt_enable( isrlevel );
+ }
+
+done:
+ return RTEMS_SUCCESSFUL;
+}
+
+
+
+
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/console/Makefile.in
new file mode 100644
index 0000000000..4c05c37698
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/Makefile.in
@@ -0,0 +1,54 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/console.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=console ns16550 z85c30 i8042vga i8042 vga
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.c
new file mode 100644
index 0000000000..6b60503ec9
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.c
@@ -0,0 +1,358 @@
+/*
+ * This file contains the TTY driver for the PPCn_60x
+ *
+ * This driver uses the termios pseudo driver.
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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.
+ *
+ * $Id$
+ */
+
+#include <bsp.h>
+#include <rtems/libio.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <termios.h>
+
+#include "console.h"
+
+/*
+ * Load configuration table
+ */
+#include "config.c"
+
+#define NUM_CONSOLE_PORTS (sizeof(Console_Port_Tbl)/sizeof(console_tbl))
+
+console_data Console_Port_Data[NUM_CONSOLE_PORTS];
+unsigned long Console_Port_Count;
+rtems_device_minor_number Console_Port_Minor;
+
+/* PAGE
+ *
+ * console_open
+ *
+ * open a port as a termios console.
+ *
+ */
+rtems_device_driver console_open(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void * arg
+)
+{
+ rtems_status_code status;
+ rtems_libio_open_close_args_t *args = arg;
+ rtems_libio_ioctl_args_t IoctlArgs;
+ struct termios Termios;
+ rtems_termios_callbacks Callbacks;
+ console_fns *c;
+
+ /*
+ * Verify the port number is valid.
+ */
+ if(minor>Console_Port_Count)
+ {
+ return RTEMS_INVALID_NUMBER;
+ }
+
+ /*
+ * open the port as a termios console driver.
+ */
+ c = Console_Port_Tbl[minor].pDeviceFns;
+ Callbacks.firstOpen = c->deviceFirstOpen;
+ Callbacks.lastClose = c->deviceLastClose;
+ Callbacks.pollRead = c->deviceRead;
+ Callbacks.write = c->deviceWrite;
+ Callbacks.setAttributes = c->deviceSetAttributes;
+ Callbacks.stopRemoteTx =
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStopRemoteTx;
+ Callbacks.startRemoteTx =
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStartRemoteTx;
+ Callbacks.outputUsesInterrupts = c->deviceOutputUsesInterrupts;
+ status = rtems_termios_open ( major, minor, arg, &Callbacks);
+ Console_Port_Data[minor].termios_data = args->iop->data1;
+
+ /*
+ * Patch in flow control routines
+ */
+/* XXX */
+#if 0
+ if((status==RTEMS_SUCCESSFUL) &&
+ (Console_Port_Tbl[minor].pDeviceFlow))
+ {
+ status=rtems_termios_flow_control(
+ major, minor, arg,
+ Console_Port_Tbl[minor].pDeviceFlow->
+ deviceStartRemoteTx,
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStopRemoteTx,
+ Console_Port_Tbl[minor].ulMargin,
+ Console_Port_Tbl[minor].ulHysteresis);
+ }
+#endif
+
+ if(minor!=Console_Port_Minor)
+ {
+ /*
+ * If this is not the console we do not want ECHO and
+ * so forth
+ */
+ IoctlArgs.iop=args->iop;
+ IoctlArgs.command=RTEMS_IO_GET_ATTRIBUTES;
+ IoctlArgs.buffer=&Termios;
+ rtems_termios_ioctl(&IoctlArgs);
+ Termios.c_lflag=ICANON;
+ IoctlArgs.command=RTEMS_IO_SET_ATTRIBUTES;
+ rtems_termios_ioctl(&IoctlArgs);
+ }
+
+ if((args->iop->flags&LIBIO_FLAGS_READ) &&
+ Console_Port_Tbl[minor].pDeviceFlow &&
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStartRemoteTx)
+ {
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStartRemoteTx(minor);
+ }
+
+ return status;
+}
+
+void console_reserve_resources(
+ rtems_configuration_table *configuration
+)
+{
+ rtems_termios_reserve_resources( configuration, 2 );
+}
+
+
+rtems_device_driver console_close(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void * arg
+)
+{
+ rtems_libio_open_close_args_t *args = arg;
+
+ if((args->iop->flags&LIBIO_FLAGS_READ) &&
+ Console_Port_Tbl[minor].pDeviceFlow &&
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStopRemoteTx)
+ {
+ Console_Port_Tbl[minor].pDeviceFlow->deviceStopRemoteTx(minor);
+ }
+
+ return rtems_termios_close (arg);
+}
+
+rtems_device_driver console_read(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void * arg
+)
+{
+ return rtems_termios_read (arg);
+}
+
+rtems_device_driver console_write(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void * arg
+)
+{
+ return rtems_termios_write (arg);
+}
+
+rtems_device_driver console_control(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void * arg
+)
+{
+ return rtems_termios_ioctl (arg);
+}
+
+/* PAGE
+ *
+ * console_initialize
+ *
+ * Routine called to initialize the console device driver.
+ */
+rtems_device_driver console_initialize(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void *arg
+)
+{
+ rtems_status_code status;
+
+ /*
+ * initialize the termio interface.
+ */
+ rtems_termios_initialize();
+
+ Console_Port_Count=NUM_CONSOLE_PORTS;
+
+ for(minor=0;
+ minor<Console_Port_Count;
+ minor++)
+ {
+ /*
+ * First perform the configuration dependant probe, then the
+ * device dependant probe
+ */
+ if((!Console_Port_Tbl[minor].deviceProbe ||
+ Console_Port_Tbl[minor].deviceProbe(minor)) &&
+ Console_Port_Tbl[minor].pDeviceFns->deviceProbe(minor))
+ {
+ /*
+ * Use this device for the console
+ */
+ break;
+ }
+ }
+ if(minor==Console_Port_Count)
+ {
+ /*
+ * Failed to find a working device
+ */
+ rtems_fatal_error_occurred(RTEMS_IO_ERROR);
+ }
+
+ Console_Port_Minor=minor;
+
+ /*
+ * Register Device Names
+ */
+ status = rtems_io_register_name("/dev/console",
+ major,
+ Console_Port_Minor );
+ if (status != RTEMS_SUCCESSFUL)
+ {
+ rtems_fatal_error_occurred(status);
+ }
+ Console_Port_Tbl[minor].pDeviceFns->deviceInitialize(
+ Console_Port_Minor);
+
+ for(minor++;minor<Console_Port_Count;minor++)
+ {
+ /*
+ * First perform the configuration dependant probe, then the
+ * device dependant probe
+ */
+ if((!Console_Port_Tbl[minor].deviceProbe ||
+ Console_Port_Tbl[minor].deviceProbe(minor)) &&
+ Console_Port_Tbl[minor].pDeviceFns->deviceProbe(minor))
+ {
+ status = rtems_io_register_name(
+ Console_Port_Tbl[minor].sDeviceName,
+ major,
+ minor );
+ if (status != RTEMS_SUCCESSFUL)
+ {
+ rtems_fatal_error_occurred(status);
+ }
+
+ /*
+ * Initialize the hardware device.
+ */
+ Console_Port_Tbl[minor].pDeviceFns->deviceInitialize(
+ minor);
+
+ }
+ }
+
+ return RTEMS_SUCCESSFUL;
+}
+
+/* PAGE
+ *
+ * DEBUG_puts
+ *
+ * This should be safe in the event of an error. It attempts to ensure
+ * that no TX empty interrupts occur while it is doing polled IO. Then
+ * it restores the state of that external interrupt.
+ *
+ * Input parameters:
+ * string - pointer to debug output string
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+
+void DEBUG_puts(
+ char *string
+)
+{
+ char *s;
+ unsigned32 Irql;
+
+ rtems_interrupt_disable(Irql);
+
+ for ( s = string ; *s ; s++ )
+ {
+ Console_Port_Tbl[Console_Port_Minor].pDeviceFns->
+ deviceWritePolled(Console_Port_Minor, *s);
+ }
+
+ rtems_interrupt_enable(Irql);
+}
+
+/* PAGE
+ *
+ * DEBUG_puth
+ *
+ * This should be safe in the event of an error. It attempts to ensure
+ * that no TX empty interrupts occur while it is doing polled IO. Then
+ * it restores the state of that external interrupt.
+ *
+ * Input parameters:
+ * ulHexNum - value to display
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+void
+DEBUG_puth(
+ unsigned32 ulHexNum
+ )
+{
+ unsigned long i,d;
+ unsigned32 Irql;
+
+ rtems_interrupt_disable(Irql);
+
+ Console_Port_Tbl[Console_Port_Minor].pDeviceFns->
+ deviceWritePolled(Console_Port_Minor, '0');
+ Console_Port_Tbl[Console_Port_Minor].pDeviceFns->
+ deviceWritePolled(Console_Port_Minor, 'x');
+
+ for(i=32;i;)
+ {
+ i-=4;
+ d=(ulHexNum>>i)&0xf;
+ Console_Port_Tbl[Console_Port_Minor].pDeviceFns->
+ deviceWritePolled(Console_Port_Minor,
+ (d<=9) ? d+'0' : d+'a'-0xa);
+ }
+
+ rtems_interrupt_enable(Irql);
+}
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.h
new file mode 100644
index 0000000000..1d6b6fc2b1
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/console.h
@@ -0,0 +1,67 @@
+/*
+ * This file contains the TTY driver table definition for the PPCn_60x
+ *
+ * This driver uses the termios pseudo driver.
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * $Id$
+ */
+
+#include <ringbuf.h>
+
+typedef struct _console_fns {
+ boolean (*deviceProbe)(int minor);
+ int (*deviceFirstOpen)(int major, int minor, void *arg);
+ int (*deviceLastClose)(int major, int minor, void *arg);
+ int (*deviceRead)(int minor);
+ int (*deviceWrite)(int minor, const char *buf, int len);
+ void (*deviceInitialize)(int minor);
+ int (*deviceSetAttributes)(int minor, const struct termios *);
+ void (*deviceWritePolled)(int minor, char cChar);
+ int deviceOutputUsesInterrupts;
+} console_fns;
+
+typedef struct _console_flow {
+ int (*deviceStopRemoteTx)(int minor);
+ int (*deviceStartRemoteTx)(int minor);
+} console_flow;
+
+typedef struct _console_tbl {
+ char *sDeviceName;
+ console_fns *pDeviceFns;
+ boolean (*deviceProbe)(int minor);
+ console_flow *pDeviceFlow;
+ unsigned32 ulMargin;
+ unsigned32 ulHysteresis;
+ void *pDeviceParams;
+ unsigned32 ulCtrlPort1;
+ unsigned32 ulCtrlPort2;
+ unsigned32 ulDataPort;
+ unsigned int ulIntVector;
+} console_tbl;
+
+typedef struct _console_data {
+ void *termios_data;
+ volatile boolean bActive;
+ volatile Ring_buffer_t TxBuffer;
+ /*
+ * This field may be used for any purpose required by the driver
+ */
+ void *pDeviceContext;
+} console_data;
+
+extern console_tbl Console_Port_Tbl[];
+extern console_data Console_Port_Data[];
+extern unsigned long Console_Port_Count;
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042.c
new file mode 100644
index 0000000000..dcfd68e72d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042.c
@@ -0,0 +1,1073 @@
+/*
+ * This file contains the PS2 keyboard driver for the i8042
+ *
+ * Note that this driver will only handle a single i8042 device
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * This driver uses the termios pseudo driver.
+ *
+ * $Id$
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+#include <rtems/libio.h>
+#include <ringbuf.h>
+
+#include "console.h"
+#include "i8042_p.h"
+#include "vga_p.h"
+
+/*
+ * UK style keyboard
+ */
+char pcUKNormalLookup[] = "1234567890-=\b\tqwertyuiop[]\n\0asdfghjkl;\'"
+ "`\0#zxcvbnm,./\0*\0 \0\0\0\0\0\0\0\0\0\0\0\0"
+ "\000789-456+1230.\0\0\\";
+char pcUKShiftedLookup[]= "!\"£$%^&*()_+\b\tQWERTYUIOP{}\n\0ASDFGHJKL:"
+ "@\0\0~ZXCVBNM<>?\0*\0 \0\0\0\0\0\0\0\0\0\0\0"
+ "\0\000789-456+1230.\0\0|";
+/*
+ * US style keyboard
+ */
+char pcUSNormalLookup[] = "1234567890-=\b\tqwertyuiop[]\n\0asdfghjkl;\'"
+ "`\0\\zxcvbnm,./\0*\0 \0\0\0\0\0\0\0\0\0\0\0"
+ "\0\000789-456+1230.\0\0\\";
+char pcUSShiftedLookup[]= "!@#$%^&*()_+\b\tQWERTYUIOP{}\n\0ASDFGHJKL:@~"
+ "\0|ZXCVBNM<>?\0*\0 \0\0\0\0\0\0\0\0\0\0\0\0"
+ "\000789-456+1230.\0\0|";
+
+static char *pcNormalLookup;
+static char *pcShiftedLookup;
+
+/*
+ * This is exported to vga.c to provide flow control
+ */
+volatile boolean bScrollLock=FALSE;
+
+/*
+ * If multiple devices are to be supported then a private copy of
+ * the following will be required for each instance
+ */
+static boolean bCtrlPressed=FALSE;
+static boolean bAltPressed=FALSE;
+static boolean bAltGrPressed=FALSE;
+static boolean bLShiftPressed=FALSE;
+static boolean bRShiftPressed=FALSE;
+static boolean bCapsLock=FALSE;
+static boolean bNumLock=FALSE;
+static boolean bTwoCode=FALSE;
+
+#if CONSOLE_USE_INTERRUPTS
+static volatile Ring_buffer_t KbdOutputBuffer;
+static volatile boolean bProcessInterruptInput=FALSE;
+static boolean bInterruptsEnabled=FALSE;
+static volatile boolean bReceivedAck=TRUE;
+
+static void i8042_process(
+ int minor
+);
+
+static void i8042_scan_code(
+ int minor,
+ unsigned8 ucScan
+);
+#endif
+
+static volatile Ring_buffer_t KbdInputBuffer;
+
+/*
+ * The following routines enable an interrupt driver to switch
+ * to polled mode as required for command processing
+ */
+void i8042_polled_on(
+ int minor
+)
+{
+#if CONSOLE_USE_INTERRUPTS
+ bProcessInterruptInput=FALSE;
+#endif
+}
+
+void i8042_polled_off(
+ int minor
+)
+{
+#if CONSOLE_USE_INTERRUPTS
+ unsigned32 Irql;
+ unsigned8 ucScan;
+
+ /*
+ * Make sure we have processed everything outstanding
+ */
+ rtems_interrupt_disable(Irql);
+ while(!Ring_buffer_Is_empty(&KbdInputBuffer))
+ {
+ rtems_interrupt_enable(Irql);
+ Ring_buffer_Remove_character(&KbdInputBuffer,
+ ucScan);
+ i8042_scan_code(minor, ucScan);
+ rtems_interrupt_disable(Irql);
+ }
+ bProcessInterruptInput=TRUE;
+ rtems_interrupt_enable(Irql);
+#endif
+}
+
+/*
+ * Send data to the keyboard
+ */
+static rtems_status_code
+i8042_outbyte_raw(
+ int minor,
+ unsigned8 ucData
+)
+{
+ unsigned32 i;
+ unsigned8 Status;
+
+#if CONSOLE_USE_INTERRUPTS
+ unsigned32 Irql;
+
+ if(bInterruptsEnabled)
+ {
+ Ring_buffer_Add_character(&KbdOutputBuffer,
+ ucData);
+ if(!Console_Port_Data[minor].bActive)
+ {
+ /*
+ * Wake up the device
+ */
+ rtems_interrupt_disable(Irql);
+ Console_Port_Data[minor].bActive=TRUE;
+ i8042_process(minor);
+ rtems_interrupt_enable(Irql);
+
+ }
+ return RTEMS_SUCCESSFUL;
+ }
+#endif
+ for (i=0; i<KBD_TIMEOUT; i++)
+ {
+ inport_byte(Console_Port_Tbl[minor].ulCtrlPort1, Status);
+ if((Status & KBD_IBF_MASK)==0)
+ {
+ outport_byte(Console_Port_Tbl[minor].ulDataPort,
+ ucData);
+ return RTEMS_SUCCESSFUL;
+ }
+ }
+ return RTEMS_TIMEOUT;
+}
+
+/*
+ * Read data from the keyboard
+ */
+static rtems_status_code
+i8042_inbyte_polled(
+ int minor,
+ unsigned8 *pucData
+)
+{
+ unsigned8 Status;
+
+ inport_byte(Console_Port_Tbl[minor].ulCtrlPort1, Status);
+ if(Status & KBD_OBF_MASK)
+ {
+ inport_byte(Console_Port_Tbl[minor].ulDataPort,
+ *pucData);
+ return RTEMS_SUCCESSFUL;
+ }
+ return RTEMS_TIMEOUT;
+}
+
+/*
+ * Blocking read data from the keyboard
+ */
+static rtems_status_code
+i8042_inbyte_raw(
+ int minor,
+ unsigned8 *pucData
+)
+{
+ int i;
+
+#if CONSOLE_USE_INTERRUPTS
+ if(bInterruptsEnabled)
+ {
+ i=0;
+ while(Ring_buffer_Is_empty(&KbdInputBuffer))
+ {
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ if(i++==KBD_TIMEOUT)
+ {
+ return RTEMS_TIMEOUT;
+ }
+ }
+ Ring_buffer_Remove_character(&KbdInputBuffer,
+ *pucData);
+ }
+ else
+#endif
+ {
+ for (i=0; i<KBD_TIMEOUT; i++)
+ {
+ if(i8042_inbyte_polled(minor, pucData)==
+ RTEMS_SUCCESSFUL)
+ {
+ return RTEMS_SUCCESSFUL;
+ }
+ /*
+ * Wait for a character to be recieved
+ */
+ }
+
+ return RTEMS_TIMEOUT;
+ }
+
+ return RTEMS_SUCCESSFUL;
+}
+
+/*
+ * Send a command to the keyboard controller
+ */
+static rtems_status_code
+i8042_outbyte_cmd_polled(
+ int minor,
+ unsigned8 ucCommand
+)
+{
+ unsigned32 i;
+ unsigned8 Status;
+
+ /*
+ * This routine may be called when no clock driver is available
+ * so the timeout is dependant on the ISA bus timing used to access
+ * the i8042 which will not vary (much) across platforms.
+ */
+ for (i=0; i<KBD_TIMEOUT; i++)
+ {
+ inport_byte(Console_Port_Tbl[minor].ulCtrlPort1, Status);
+ if((Status & KBD_IBF_MASK)==0)
+ {
+ outport_byte(Console_Port_Tbl[minor].ulCtrlPort1,
+ ucCommand);
+ return RTEMS_SUCCESSFUL;
+ }
+ }
+ return RTEMS_TIMEOUT;
+}
+
+void EnqueueKbdChar(
+ int minor,
+ char cChar
+)
+{
+#if CONSOLE_USE_INTERRUPTS
+ rtems_termios_enqueue_raw_characters(
+ Console_Port_Data[minor].termios_data,
+ &cChar,
+ 1);
+#else
+ Ring_buffer_Add_character(&KbdInputBuffer, cChar);
+#endif
+}
+/*
+ * Process second code in a two code sequence
+ */
+static void i8042_process_two_code(
+ int minor,
+ unsigned8 ucScan,
+ boolean bMakenBreak
+)
+{
+ char cASCIICtrlCode;
+ char cASCIICode;
+
+ cASCIICtrlCode='\0';
+ cASCIICode='\0';
+
+ switch(ucScan)
+ {
+ case KEY_ALT:
+ {
+ bAltGrPressed=bMakenBreak;
+ break;
+ }
+
+ case KEY_CONTROL:
+ {
+ bCtrlPressed=bMakenBreak;
+ break;
+ }
+
+ case KEY_INSERT:
+ {
+ cASCIICtrlCode='@';
+ break;
+ }
+
+ case KEY_DELETE:
+ {
+ cASCIICode=ASCII_DEL;
+ break;
+ }
+
+ case KEY_LEFT_ARROW:
+ {
+ cASCIICtrlCode='D';
+ break;
+ }
+
+ case KEY_HOME:
+ {
+ cASCIICtrlCode='H';
+ break;
+ }
+
+ case KEY_END:
+ {
+ cASCIICtrlCode='K';
+ break;
+ }
+
+ case KEY_UP_ARROW:
+ {
+ cASCIICtrlCode='A';
+ break;
+ }
+
+ case KEY_DOWN_ARROW:
+ {
+ cASCIICtrlCode='B';
+ break;
+ }
+
+ case KEY_PAGE_UP:
+ {
+ cASCIICtrlCode='?';
+ break;
+ }
+
+ case KEY_PAGE_DOWN:
+ {
+ cASCIICtrlCode='/';
+ break;
+ }
+
+ case KEY_RIGHT_ARROW:
+ {
+ cASCIICtrlCode='C';
+ break;
+ }
+
+ case KEY_KEYPAD_SLASH:
+ {
+ cASCIICode='/';
+ break;
+ }
+
+ case KEY_KEYPAD_ENTER:
+ {
+ cASCIICode=ASCII_CR;
+ break;
+ }
+
+ case KEY_PRINT_SCREEN:
+ {
+ cASCIICode=ASCII_SYSRQ;
+ break;
+ }
+
+ default:
+ {
+ /*
+ * Ignore this code
+ */
+ break;
+ }
+ }
+
+ if(bMakenBreak && cASCIICode)
+ {
+ EnqueueKbdChar(minor, cASCIICode);
+ }
+ else if(bMakenBreak && cASCIICtrlCode)
+ {
+ EnqueueKbdChar(minor, ASCII_CSI);
+ EnqueueKbdChar(minor, cASCIICtrlCode);
+ }
+}
+
+static boolean i8042_process_qualifiers(
+ unsigned8 ucScan,
+ boolean bMakenBreak
+)
+{
+ boolean bProcessed;
+
+ /*
+ * Check for scan codes for shift, control, or alt keys.
+ */
+ bProcessed=TRUE;
+
+ switch (ucScan)
+ {
+ case KEY_LEFT_SHIFT:
+ {
+ bLShiftPressed=bMakenBreak;
+ break;
+ }
+
+ case KEY_RIGHT_SHIFT:
+ {
+ bRShiftPressed=bMakenBreak;
+ break;
+ }
+
+ case KEY_CONTROL:
+ {
+ bCtrlPressed=bMakenBreak;
+ break;
+ }
+
+ case KEY_ALT:
+ {
+ bAltPressed=bMakenBreak;
+ break;
+ }
+
+ default:
+ {
+ /*
+ * Something else needs to process this code
+ */
+ bProcessed=FALSE;
+ break;
+ }
+ }
+
+ return(bProcessed);
+}
+
+static boolean i8042_process_top_row(
+ int minor,
+ unsigned8 ucScan
+)
+{
+ boolean bProcessed;
+ char cASCIIFnCode;
+#if CONSOLE_USE_INTERRUPTS==0
+ unsigned8 ucKeyboardAck;
+#endif
+
+ /*
+ * Check for keys on the top row
+ */
+ bProcessed=TRUE;
+ cASCIIFnCode='\0';
+
+ switch (ucScan)
+ {
+ case KEY_ESC:
+ {
+ EnqueueKbdChar(minor, ASCII_ESC);
+ break;
+ }
+
+ case KEY_F1:
+ {
+ cASCIIFnCode='P';
+ break;
+ }
+
+ case KEY_F2:
+ {
+ cASCIIFnCode='Q';
+ break;
+ }
+
+ case KEY_F3:
+ {
+ cASCIIFnCode='w';
+ break;
+ }
+
+ case KEY_F4:
+ {
+ cASCIIFnCode='x';
+ break;
+ }
+
+ case KEY_F5:
+ {
+ cASCIIFnCode='t';
+ break;
+ }
+
+ case KEY_F6:
+ {
+ cASCIIFnCode='u';
+ break;
+ }
+
+ case KEY_F7:
+ {
+ cASCIIFnCode='q';
+ break;
+ }
+
+ case KEY_F8:
+ {
+ cASCIIFnCode='r';
+ break;
+ }
+
+ case KEY_F9:
+ {
+ cASCIIFnCode='p';
+ break;
+ }
+
+ case KEY_F10:
+ {
+ cASCIIFnCode='M';
+ break;
+ }
+
+ case KEY_F11:
+ {
+ cASCIIFnCode='A';
+ break;
+ }
+
+ case KEY_F12:
+ {
+ cASCIIFnCode='B';
+ break;
+ }
+
+ case KEY_SYS_REQUEST:
+ {
+ EnqueueKbdChar(minor, ASCII_SYSRQ);
+ break;
+ }
+
+ case KEY_CAPS_LOCK:
+ case KEY_NUM_LOCK:
+ case KEY_SCROLL_LOCK:
+ {
+ switch(ucScan)
+ {
+ case KEY_CAPS_LOCK:
+ {
+ bCapsLock=!bCapsLock;
+ break;
+ }
+
+ case KEY_NUM_LOCK:
+ {
+ bNumLock=!bNumLock;
+ break;
+ }
+
+ case KEY_SCROLL_LOCK:
+ {
+#if CONSOLE_USE_INTERRUPTS
+ bScrollLock=!bScrollLock;
+#endif
+ break;
+ }
+ }
+
+ i8042_outbyte_raw(minor, KBD_CMD_SET_LEDS);
+#if CONSOLE_USE_INTERRUPTS==0
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+#endif
+ i8042_outbyte_raw(minor,
+ (bCapsLock ? KBD_LED_CAPS : 0) |
+ (bNumLock ? KBD_LED_NUM : 0) |
+ (bScrollLock ? KBD_LED_SCROLL : 0));
+#if CONSOLE_USE_INTERRUPTS==0
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+#endif
+
+ break;
+ }
+
+ default:
+ {
+ /*
+ * Something else needs to process this code
+ */
+ bProcessed=FALSE;
+ break;
+ }
+ }
+
+ if(cASCIIFnCode)
+ {
+ EnqueueKbdChar(minor, ASCII_CSI);
+ EnqueueKbdChar(minor, 'O');
+ EnqueueKbdChar(minor, cASCIIFnCode);
+ }
+
+ return(bProcessed);
+}
+
+static boolean i8042_process_keypad(
+ int minor,
+ unsigned8 ucScan
+)
+{
+ char cASCIICtrlCode;
+
+ /*
+ * Process keys on the keypad
+ */
+ cASCIICtrlCode='\0';
+
+ switch(ucScan)
+ {
+ case KEY_UP_ARROW:
+ {
+ cASCIICtrlCode='A';
+ break;
+ }
+
+ case KEY_DOWN_ARROW:
+ {
+ cASCIICtrlCode='B';
+ break;
+ }
+
+ case KEY_RIGHT_ARROW:
+ {
+ cASCIICtrlCode='C';
+ break;
+ }
+
+ case KEY_LEFT_ARROW:
+ {
+ cASCIICtrlCode='D';
+ break;
+ }
+
+ case KEY_HOME:
+ {
+ cASCIICtrlCode='H';
+ break;
+ }
+
+ case KEY_END:
+ {
+ cASCIICtrlCode='K';
+ break;
+ }
+
+ case KEY_PAGE_UP:
+ {
+ cASCIICtrlCode='?';
+ break;
+ }
+
+ case KEY_PAGE_DOWN:
+ {
+ cASCIICtrlCode='/';
+ break;
+ }
+
+ case KEY_INSERT:
+ {
+ cASCIICtrlCode='@';
+ break;
+ }
+
+ case KEY_DELETE:
+ {
+ /*
+ * This is a special case not requiring an ASCII_CSI
+ */
+ EnqueueKbdChar(minor, ASCII_DEL);
+ return(TRUE);
+ }
+
+ default:
+ {
+ /*
+ * Something else needs to process this code
+ */
+ break;
+ }
+ }
+
+ if(cASCIICtrlCode)
+ {
+ EnqueueKbdChar(minor, ASCII_CSI);
+ EnqueueKbdChar(minor, cASCIICtrlCode);
+ return(TRUE);
+ }
+ else
+ {
+ return(FALSE);
+ }
+}
+
+/*
+ * This routine translates the keyboard scan code into an
+ * ASCII character (or sequence) and queues it
+ */
+static void i8042_scan_code(
+ int minor,
+ unsigned8 ucScan
+)
+{
+ char cChar;
+ boolean bMakenBreak;
+
+ /*
+ * Check for code 0xe0, which introduces a two key sequence.
+ */
+
+ if(ucScan==KEY_TWO_KEY)
+ {
+ bTwoCode=TRUE;
+ return;
+ }
+
+ /*
+ * Bit 7 of scan code indicates make or break
+ */
+ if(ucScan & 0x80)
+ {
+ bMakenBreak=FALSE;
+ ucScan&=0x7f;
+ }
+ else
+ {
+ bMakenBreak=TRUE;
+ }
+
+ /*
+ * If we are in a multikey sequence then process the second keypress
+ */
+ if(bTwoCode)
+ {
+ i8042_process_two_code(minor, ucScan, bMakenBreak);
+
+ /*
+ * Revert to prcessing single key sequences
+ */
+ bTwoCode=FALSE;
+ return;
+ }
+
+ if(i8042_process_qualifiers(ucScan, bMakenBreak))
+ {
+ /*
+ * We are all done
+ */
+ return;
+ }
+
+ /*
+ * The remaining keys are only processed for make
+ */
+ if(!bMakenBreak)
+ {
+ return;
+ }
+
+ if(i8042_process_top_row(minor, ucScan))
+ {
+ /*
+ * We are all done
+ */
+ return;
+ }
+
+ if(!bNumLock && i8042_process_keypad(minor, ucScan))
+ {
+ /*
+ * We are all done
+ */
+ return;
+ }
+
+ /*
+ * Process "normal" keys
+ */
+
+ cChar=0;
+
+ /*
+ * Check to see if the scan code corresponds to an ASCII
+ * character.
+ */
+ if(((ucScan >= 16) && (ucScan <= 25)) ||
+ ((ucScan >= 30) && (ucScan <= 38)) ||
+ ((ucScan >= 44) && (ucScan <= 50)))
+ {
+ if(bCtrlPressed)
+ {
+ cChar=pcNormalLookup[ucScan - 2]-'a'+1;
+ }
+ else
+ {
+ if(((bLShiftPressed || bRShiftPressed) && !bCapsLock) ||
+ (!(bLShiftPressed || bRShiftPressed) && bCapsLock))
+ {
+ cChar=pcShiftedLookup[ucScan - 2];
+ }
+ else
+ {
+ cChar=pcNormalLookup[ucScan - 2];
+ }
+ }
+ }
+ else if((ucScan > 1) && (ucScan <= 0x56))
+ {
+ /*
+ * Its ASCII but not alpha, so don't shift on CapsLock.
+ */
+ if(bLShiftPressed || bRShiftPressed)
+ {
+ cChar=pcShiftedLookup[ucScan - 2];
+ }
+ else
+ {
+ cChar=pcNormalLookup[ucScan - 2];
+ }
+ }
+
+ /*
+ * If we got a character then queue it
+ */
+ if(cChar)
+ {
+ EnqueueKbdChar(minor, cChar);
+ }
+}
+
+/*
+ * Console Device Driver Entry Points
+ */
+boolean i8042_probe(int minor)
+{
+ unsigned8 ucKeyboardAck;
+ unsigned8 ucKeyboardID1, ucKeyboardID2;
+
+ if(!vga_probe(minor))
+ {
+ /*
+ * There is no VGA adaptor so fail probe
+ */
+ return(FALSE);
+ }
+
+ Ring_buffer_Initialize(&KbdInputBuffer);
+#if CONSOLE_USE_INTERRUPTS
+ Ring_buffer_Initialize(&KbdOutputBuffer);
+#endif
+
+ i8042_polled_on(minor);
+ /*
+ * Determine keyboard type
+ */
+ i8042_outbyte_raw(minor, KBD_CMD_READ_ID);
+ ucKeyboardAck=0;
+ if((i8042_inbyte_raw(minor, &ucKeyboardAck)==RTEMS_TIMEOUT) ||
+ (ucKeyboardAck==KBD_CMD_RESEND))
+ {
+ /*
+ * No or incorrect keyboard response so fail probe
+ */
+ return(FALSE);
+ }
+
+ i8042_inbyte_raw(minor, &ucKeyboardID1);
+ i8042_inbyte_raw(minor, &ucKeyboardID2);
+ if((ucKeyboardID1==0xab) && (ucKeyboardID2==0x41))
+ {
+ pcNormalLookup=&pcUKNormalLookup[0];
+ pcShiftedLookup=&pcUKShiftedLookup[0];
+ }
+ else
+ {
+ pcNormalLookup=&pcUSNormalLookup[0];
+ pcShiftedLookup=&pcUSShiftedLookup[0];
+ }
+ i8042_polled_off(minor);
+
+ return(TRUE);
+}
+
+void i8042_init(int minor)
+{
+ unsigned8 ucKeyboardAck;
+
+ vga_init(minor);
+
+ i8042_polled_on(minor);
+ /*
+ * Switch all LEDs off
+ */
+ i8042_outbyte_raw(minor, KBD_CMD_SET_LEDS);
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+ i8042_outbyte_raw(minor, 0);
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+ /*
+ * Select scan code set 1
+ */
+ i8042_outbyte_raw(minor, KBD_CMD_SEL_SCAN_CODE);
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+ i8042_outbyte_raw(minor, 1);
+ i8042_inbyte_raw(minor, &ucKeyboardAck);
+ i8042_polled_off(minor);
+}
+
+/* PAGE
+ *
+ * i8042_inbyte_nonblocking_polled
+ *
+ * Console Termios polling input entry point.
+ */
+
+int i8042_inbyte_nonblocking_polled(
+ int minor
+)
+{
+ unsigned8 ucScan;
+ char ucData;
+
+ if(i8042_inbyte_polled(minor, &ucScan)==RTEMS_SUCCESSFUL)
+ {
+ i8042_scan_code(minor, ucScan);
+ }
+
+ if(!Ring_buffer_Is_empty(&KbdInputBuffer))
+ {
+ Ring_buffer_Remove_character(&KbdInputBuffer,
+ ucData);
+ return(ucData);
+ }
+
+ return(-1);
+}
+
+#if CONSOLE_USE_INTERRUPTS
+/*
+ * i8042_isr
+ *
+ * This routine is the console interrupt handler for the keyboard
+ *
+ * Input parameters:
+ * vector - vector number
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+static void i8042_process(
+ int minor
+)
+{
+ unsigned8 Status;
+ unsigned8 ucData;
+
+ inport_byte(Console_Port_Tbl[minor].ulCtrlPort1, Status);
+
+ if(Status & KBD_OBF_MASK)
+ {
+ inport_byte(Console_Port_Tbl[minor].ulDataPort, ucData);
+
+ if(bProcessInterruptInput)
+ {
+ /*
+ * Every byte written to the keyboard should be followed
+ * by an acknowledge
+ */
+ if(ucData==KBD_CMD_ACK)
+ {
+ bReceivedAck=TRUE;
+ }
+ else
+ {
+ i8042_scan_code(minor, ucData);
+ }
+ }
+ else
+ {
+ /*
+ * Store the scan code into the ring buffer where it
+ * can be read using i8042_inbyte_raw()
+ */
+ Ring_buffer_Add_character(&KbdInputBuffer, ucData);
+ }
+ }
+
+ if(((Status & KBD_IBF_MASK)==0) &&
+ bReceivedAck)
+ {
+ if(Ring_buffer_Is_empty(&KbdOutputBuffer))
+ {
+ Console_Port_Data[minor].bActive=FALSE;
+ }
+ else
+ {
+ Ring_buffer_Remove_character(&KbdOutputBuffer,
+ ucData);
+ outport_byte(Console_Port_Tbl[minor].ulDataPort,
+ ucData);
+ bReceivedAck=FALSE;
+ }
+ }
+}
+
+static rtems_isr i8042_isr(
+ rtems_vector_number vector
+)
+{
+ int minor;
+
+ for(minor=0;minor<Console_Port_Count;minor++)
+ {
+ if(vector==Console_Port_Tbl[minor].ulIntVector)
+ {
+ i8042_process(minor);
+ }
+ }
+}
+
+void i8042_initialize_interrupts(int minor)
+{
+ i8042_init(minor);
+
+ Console_Port_Data[minor].bActive=FALSE;
+
+ set_vector(i8042_isr,
+ Console_Port_Tbl[minor].ulIntVector,
+ 1);
+
+ i8042_outbyte_cmd_polled(minor, KBD_CTR_WRITE_COMMAND);
+ i8042_outbyte_raw(minor, KBD_CMD_ENABLE_KBD_INT);
+
+ /*
+ * At this point interrupts should spring into life
+ */
+ bInterruptsEnabled=TRUE;
+}
+
+#endif /* CONSOLE_USE_INTERRUPTS */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042_p.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042_p.h
new file mode 100644
index 0000000000..57273fbe7f
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042_p.h
@@ -0,0 +1,196 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#ifndef _I8042_P_H_
+#define _I8042_P_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define KBD_CTR_WRITE_COMMAND 0x60
+#define KBD_CTR_READ_COMMAND 0x20
+#define KBD_CTR_TEST_PASSWORD 0xA4
+#define KBD_CTR_LOAD_PASSWORD 0xA5
+#define KBD_CTR_ENABLE_PASSWORD 0xA6
+#define KBD_CTR_DISABLE_AUX 0xA7
+#define KBD_CTR_ENABLE_AUX 0xA8
+#define KBD_CTR_AUXLINES_TEST 0xA9
+#define KBD_CTR_SELFTEST 0xAA
+#define KBD_CTR_KBDLINES_TEST 0xAB
+#define KBD_CTR_DISABLE_KBD 0xAD
+#define KBD_CTR_ENABLE_KBD 0xAE
+#define KBD_CTR_WRITE_AUX 0xD4
+#define KBD_CTR_READ_REV 0xD5
+#define KBD_CTR_READ_VER 0xD6
+#define KBD_CTR_READ_MODEL 0xD7
+
+/* Keyboard Controller Data */
+#define KBD_CTR_SELFTEST_PASSED 0x55
+#define KBD_CTR_PASSWORD_INSTALLED 0xFA
+#define KBD_CTR_PASSWORD_NOT_INSTALLED 0xF1
+
+/* Controller Command Byte bit definitions. */
+#define KBD_CMD_BYTE_DISABLE_AUX 0x20
+#define KBD_CMD_BYTE_DISABLE_KBD 0x10
+#define KBD_CMD_ENABLE_AUX_INT 0x02
+#define KBD_CMD_ENABLE_KBD_INT 0x01
+
+/* Keyboard Controller Status byte masks */
+#define KBD_OBF_MASK 0x1 /* Output buffer full */
+#define KBD_IBF_MASK 0x2 /* Input buffer full */
+#define KBD_FROM_AUX_MASK 0x20 /* Byte from Aux Port. */
+
+/* Interface Test Results */
+#define INTERFACE_NO_ERROR 0x00
+#define CLOCK_STUCK_LOW 0x01
+#define CLOCK_STUCK_HIGH 0x02
+#define DATA_STUCK_LOW 0x03
+#define DATA_STUCK_HIGH 0x04
+
+/* Timeout */
+#define KBD_TIMEOUT 500000 /* Effectively ISA read access times */
+
+/* Keyboard Commands */
+#define KBD_CMD_SET_LEDS 0xed /* Set/Reset LEDs */
+#define KBD_CMD_ECHO 0xee /* request keyboard echo resp. "EE" */
+#define KBD_CMD_SEL_SCAN_CODE 0xf0 /* Scan codes 1,2,3 or 0 = rquest current. */
+#define KBD_CMD_READ_ID 0xf2 /* Request for two byte response */
+#define KBD_CMD_SET_RATE 0xf3 /* Set tellematic Rate */
+#define KBD_CMD_ENABLE 0xf4 /* Clears Buffer and Starts Scanning. */
+#define KBD_CMD_DISABLE 0xf5 /* reset to power up */
+
+#define KBD_CMD_SET_DEFAULT 0xf6
+#define KBD_CMD_SET_ALL_TLMTIC 0xf7 /* Set all keys telematic */
+#define KBD_CMD_SET_ALL_MKBR 0xf8 /* Set all keys Make /Break */
+#define KBD_CMD_SET_ALL_MAKE 0xf9 /* Set all keys Make only */
+#define KBD_CMD_SET_KEY_TLMTIC 0xfb /* Set individual key telemativ */
+#define KBD_CMD_SET_KEY_MKBR 0xfc /* set individual key make/break */
+#define KBD_CMD_SET_KEY_MK 0xfd /* set individual key make only */
+#define KBD_CMD_RESEND 0xfe /* request to resend last transfer */
+#define KBD_CMD_RESET 0xff /* request to start a program reset */
+#define KBD_CMD_ACK 0xfa /* keyboard ack after reset */
+#define KBD_CMD_BAT 0xaa /* Keyboard Bat completion Response */
+
+/*
+ * Define LED encodings for use with the KbdSetLEDs command
+ */
+#define KBD_LED_CAPS 0x04
+#define KBD_LED_NUM 0x02
+#define KBD_LED_SCROLL 0x01
+
+/*
+ * Define two code scan codes in keycode order
+ */
+#define KEY_TWO_KEY 0xe0
+#define KEY_ALT 0x38
+#define KEY_CONTROL 0x1d
+#define KEY_INSERT 0x52
+#define KEY_DELETE 0x53
+#define KEY_LEFT_ARROW 0x4b
+#define KEY_HOME 0x47
+#define KEY_END 0x4F
+#define KEY_UP_ARROW 0x48
+#define KEY_DOWN_ARROW 0x50
+#define KEY_PAGE_UP 0x49
+#define KEY_PAGE_DOWN 0x51
+#define KEY_RIGHT_ARROW 0x4d
+#define KEY_KEYPAD_SLASH 0x35
+#define KEY_KEYPAD_ENTER 0x1c
+#define KEY_SYS_REQUEST 0x2a
+#define KEY_PRINT_SCREEN 0x37
+
+#define KEY_LEFT_SHIFT 0x2a
+#define KEY_RIGHT_SHIFT 0x36
+#define KEY_TAB 0x0f
+#define KEY_CAPS_LOCK 0x3a
+#define KEY_NUM_LOCK 0x45
+#define KEY_SCROLL_LOCK 0x46
+#define KEY_ESC 0x01
+#define KEY_F1 0x3b
+#define KEY_F2 0x3c
+#define KEY_F3 0x3d
+#define KEY_F4 0x3e
+#define KEY_F5 0x3f
+#define KEY_F6 0x40
+#define KEY_F7 0x41
+#define KEY_F8 0x42
+#define KEY_F9 0x43
+#define KEY_F10 0x44
+#define KEY_F11 0x57
+#define KEY_F12 0x58
+
+/*
+ * ASCII control codes
+ */
+#define ASCII_NUL 0x00
+#define ASCII_SOH 0x01
+#define ASCII_STX 0x02
+#define ASCII_ETX 0x03
+#define ASCII_EOT 0x04
+#define ASCII_ENQ 0x05
+#define ASCII_ACK 0x06
+#define ASCII_BEL 0x07
+#define ASCII_BS 0x08
+#define ASCII_HT 0x09
+#define ASCII_LF 0x0a
+#define ASCII_VT 0x0b
+#define ASCII_FF 0x0c
+#define ASCII_CR 0x0d
+#define ASCII_SO 0x0e
+#define ASCII_SI 0x0f
+#define ASCII_DLE 0x10
+#define ASCII_XON 0x11
+#define ASCII_DC1 0x11
+#define ASCII_DC2 0x12
+#define ASCII_XOFF 0x13
+#define ASCII_DC3 0x13
+#define ASCII_DC4 0x14
+#define ASCII_NAK 0x15
+#define ASCII_SYN 0x16
+#define ASCII_ETB 0x17
+#define ASCII_CAN 0x18
+#define ASCII_EM 0x19
+#define ASCII_SUB 0x1a
+#define ASCII_ESC 0x1b
+#define ASCII_FS 0x1c
+#define ASCII_GS 0x1d
+#define ASCII_RS 0x1e
+#define ASCII_US 0x1f
+#define ASCII_DEL 0x7f
+#define ASCII_SYSRQ 0x80
+#define ASCII_CSI 0x9b
+
+/*
+ * Exported functions
+ */
+extern boolean i8042_probe(int minor);
+
+extern void i8042_init(int minor);
+#if CONSOLE_USE_INTERRUPTS
+extern void i8042_initialize_interrupts(int minor);
+
+#else
+extern int i8042_inbyte_nonblocking_polled(
+ int minor
+);
+#endif /* CONSOLE_USE_INTERRUPTS */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _I8042_P_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.c
new file mode 100644
index 0000000000..59716da49a
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.c
@@ -0,0 +1,46 @@
+/*
+ * This file contains the TTY driver for the VGA/i8042 console
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * This driver uses the termios pseudo driver.
+ *
+ * $Id$
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+#include <rtems/libio.h>
+
+#include "console.h"
+#include "vga_p.h"
+#include "i8042_p.h"
+
+console_fns i8042vga_fns =
+{
+ i8042_probe, /* deviceProbe */
+ NULL, /* deviceFirstOpen */
+ NULL, /* deviceLastClose */
+#if CONSOLE_USE_INTERRUPTS
+ NULL, /* deviceRead */
+ vga_write_support, /* deviceWrite */
+ i8042_initialize_interrupts, /* deviceInitialize */
+#else
+ i8042_inbyte_nonblocking_polled, /* deviceRead */
+ vga_write_support, /* deviceWrite */
+ i8042_init, /* deviceInitialize */
+#endif
+ vga_write, /* deviceWritePolled */
+ FALSE, /* deviceOutputUsesInterrupts */
+};
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.h
new file mode 100644
index 0000000000..6cbceb92de
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/i8042vga.h
@@ -0,0 +1,34 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * $Id$
+ */
+
+#ifndef _I8042VGA_H_
+#define _I8042VGA_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * Driver function table
+ */
+extern console_fns i8042vga_fns;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _I8042VGA_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.c
new file mode 100644
index 0000000000..30c10f73b2
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.c
@@ -0,0 +1,632 @@
+/*
+ * This file contains the TTY driver for the NS16550
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * This driver uses the termios pseudo driver.
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+#include <rtems/libio.h>
+#include <stdlib.h>
+
+#include "console.h"
+#include "ns16550_p.h"
+
+/*
+ * Flow control is only supported when using interrupts
+ */
+console_flow ns16550_flow_RTSCTS =
+{
+ ns16550_negate_RTS, /* deviceStopRemoteTx */
+ ns16550_assert_RTS /* deviceStartRemoteTx */
+};
+
+console_flow ns16550_flow_DTRCTS =
+{
+ ns16550_negate_DTR, /* deviceStopRemoteTx */
+ ns16550_assert_DTR /* deviceStartRemoteTx */
+};
+
+console_fns ns16550_fns =
+{
+ ns16550_probe, /* deviceProbe */
+ ns16550_open, /* deviceFirstOpen */
+ ns16550_flush, /* deviceLastClose */
+ NULL, /* deviceRead */
+ ns16550_write_support_int, /* deviceWrite */
+ ns16550_initialize_interrupts, /* deviceInitialize */
+ ns16550_write_polled, /* deviceWritePolled */
+ FALSE, /* deviceOutputUsesInterrupts */
+};
+
+console_fns ns16550_fns_polled =
+{
+ ns16550_probe, /* deviceProbe */
+ ns16550_open, /* deviceFirstOpen */
+ ns16550_close, /* deviceLastClose */
+ ns16550_inbyte_nonblocking_polled, /* deviceRead */
+ ns16550_write_support_polled, /* deviceWrite */
+ ns16550_init, /* deviceInitialize */
+ ns16550_write_polled, /* deviceWritePolled */
+ FALSE, /* deviceOutputUsesInterrupts */
+};
+
+/*
+ * Console Device Driver Entry Points
+ */
+static boolean ns16550_probe(int minor)
+{
+ /*
+ * If the configuration dependant probe has located the device then
+ * assume it is there
+ */
+ return(TRUE);
+}
+
+static void ns16550_init(int minor)
+{
+ PSP_READ_REGISTERS pNS16550Read;
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned8 ucTrash;
+ unsigned8 ucDataByte;
+ unsigned32 ulBaudDivisor;
+ ns16550_context *pns16550Context;
+
+ pns16550Context=(ns16550_context *)malloc(sizeof(ns16550_context));
+
+ Console_Port_Data[minor].pDeviceContext=(void *)pns16550Context;
+ pns16550Context->ucModemCtrl=SP_MODEM_IRQ;
+
+ pNS16550Read=(PSP_READ_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+ pNS16550Write=(PSP_WRITE_REGISTERS)pNS16550Read;
+
+ /* Clear the divisor latch, clear all interrupt enables,
+ * and reset and
+ * disable the FIFO's.
+ */
+
+ outport_byte(&pNS16550Write->LineControl, 0x0);
+ outport_byte(&pNS16550Write->InterruptEnable, 0x0);
+
+ /* Set the divisor latch and set the baud rate. */
+
+ ulBaudDivisor=NS16550_Baud(
+ (unsigned32)Console_Port_Tbl[minor].pDeviceParams);
+ ucDataByte = SP_LINE_DLAB;
+ outport_byte(&pNS16550Write->LineControl, ucDataByte);
+ outport_byte(&pNS16550Write->TransmitBuffer, ulBaudDivisor&0xff);
+ outport_byte(&pNS16550Write->InterruptEnable, (ulBaudDivisor>>8)&0xff);
+
+ /* Clear the divisor latch and set the character size to eight bits */
+ /* with one stop bit and no parity checking. */
+
+ ucDataByte = EIGHT_BITS;
+ outport_byte(&pNS16550Write->LineControl, ucDataByte);
+
+ /* Enable and reset transmit and receive FIFOs. TJA */
+ ucDataByte = SP_FIFO_ENABLE;
+ outport_byte(&pNS16550Write->FifoControl, ucDataByte);
+
+ ucDataByte = SP_FIFO_ENABLE | SP_FIFO_RXRST | SP_FIFO_TXRST;
+ outport_byte(&pNS16550Write->FifoControl, ucDataByte);
+
+ /*
+ * Disable interrupts
+ */
+ ucDataByte = 0;
+ outport_byte(&pNS16550Write->InterruptEnable, ucDataByte);
+
+ /* Set data terminal ready. */
+ /* And open interrupt tristate line */
+
+ outport_byte(&pNS16550Write->ModemControl,
+ pns16550Context->ucModemCtrl);
+
+ inport_byte(&pNS16550Read->LineStatus, ucTrash);
+ inport_byte(&pNS16550Read->ReceiveBuffer, ucTrash);
+}
+
+static int ns16550_open(
+ int major,
+ int minor,
+ void * arg
+)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Assert DTR
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&ns16550_flow_DTRCTS)
+ {
+ ns16550_assert_DTR(minor);
+ }
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+static int ns16550_close(
+ int major,
+ int minor,
+ void * arg
+)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Negate DTR
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&ns16550_flow_DTRCTS)
+ {
+ ns16550_negate_DTR(minor);
+ }
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * ns16550_write_polled
+ */
+static void ns16550_write_polled(
+ int minor,
+ char cChar
+)
+{
+ PSP_READ_REGISTERS pNS16550Read;
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned char ucLineStatus;
+ int iTimeout;
+
+ pNS16550Read=(PSP_READ_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+ pNS16550Write=(PSP_WRITE_REGISTERS)pNS16550Read;
+
+ /*
+ * wait for transmitter holding register to be empty
+ */
+ iTimeout=1000;
+ inport_byte(&pNS16550Read->LineStatus, ucLineStatus);
+ while ((ucLineStatus & SP_LSR_THOLD) == 0)
+ {
+ /*
+ * Yield while we wait
+ */
+ if(_System_state_Is_up(_System_state_Get()))
+ {
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+ inport_byte(&pNS16550Read->LineStatus, ucLineStatus);
+ if(!--iTimeout)
+ {
+ break;
+ }
+ }
+
+ /*
+ * transmit character
+ */
+ outport_byte(&pNS16550Write->TransmitBuffer, cChar);
+}
+
+/*
+ * These routines provide control of the RTS and DTR lines
+ */
+/*
+ * ns16550_assert_RTS
+ */
+static void ns16550_assert_RTS(int minor)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned32 Irql;
+ ns16550_context *pns16550Context;
+
+ pns16550Context=(ns16550_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Assert RTS
+ */
+ rtems_interrupt_disable(Irql);
+ pns16550Context->ucModemCtrl|=SP_MODEM_RTS;
+ outport_byte(&pNS16550Write->ModemControl,
+ pns16550Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * ns16550_negate_RTS
+ */
+static void ns16550_negate_RTS(int minor)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned32 Irql;
+ ns16550_context *pns16550Context;
+
+ pns16550Context=(ns16550_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Negate RTS
+ */
+ rtems_interrupt_disable(Irql);
+ pns16550Context->ucModemCtrl&=~SP_MODEM_RTS;
+ outport_byte(&pNS16550Write->ModemControl,
+ pns16550Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * These flow control routines utilise a connection from the local DTR
+ * line to the remote CTS line
+ */
+/*
+ * ns16550_assert_DTR
+ */
+static void ns16550_assert_DTR(int minor)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned32 Irql;
+ ns16550_context *pns16550Context;
+
+ pns16550Context=(ns16550_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Assert DTR
+ */
+ rtems_interrupt_disable(Irql);
+ pns16550Context->ucModemCtrl|=SP_MODEM_DTR;
+ outport_byte(&pNS16550Write->ModemControl,
+ pns16550Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * ns16550_negate_DTR
+ */
+static void ns16550_negate_DTR(int minor)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned32 Irql;
+ ns16550_context *pns16550Context;
+
+ pns16550Context=(ns16550_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Negate DTR
+ */
+ rtems_interrupt_disable(Irql);
+ pns16550Context->ucModemCtrl&=~SP_MODEM_DTR;
+ outport_byte(&pNS16550Write->ModemControl,
+ pns16550Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * ns16550_isr
+ *
+ * This routine is the console interrupt handler for COM1 and COM2
+ *
+ * Input parameters:
+ * vector - vector number
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+
+static void ns16550_process(
+ int minor
+)
+{
+ PSP_READ_REGISTERS pNS16550Read;
+ PSP_WRITE_REGISTERS pNS16550Write;
+ volatile unsigned8 ucLineStatus, ucInterruptId;
+ char cChar;
+
+ pNS16550Read=(PSP_READ_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+ pNS16550Write=(PSP_WRITE_REGISTERS)pNS16550Read;
+
+ do
+ {
+ /*
+ * Deal with any received characters
+ */
+ while(TRUE)
+ {
+ inport_byte(&pNS16550Read->LineStatus, ucLineStatus);
+ if(~ucLineStatus & SP_LSR_RDY)
+ {
+ break;
+ }
+ inport_byte(&pNS16550Read->ReceiveBuffer, cChar);
+ rtems_termios_enqueue_raw_characters(
+ Console_Port_Data[minor].termios_data,
+ &cChar, 1 );
+ }
+
+ while(TRUE)
+ {
+ if(Ring_buffer_Is_empty(
+ &Console_Port_Data[minor].TxBuffer))
+ {
+ Console_Port_Data[minor].bActive=FALSE;
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&ns16550_flow_RTSCTS)
+ {
+ ns16550_negate_RTS(minor);
+ }
+ /*
+ * There is no data to transmit
+ */
+ break;
+ }
+
+ inport_byte(&pNS16550Read->LineStatus, ucLineStatus);
+ if(~ucLineStatus & SP_LSR_THOLD)
+ {
+ /*
+ * We'll get another interrupt when
+ * the transmitter holding reg. becomes
+ * free again
+ */
+ break;
+ }
+
+ Ring_buffer_Remove_character(
+ &Console_Port_Data[minor].TxBuffer,
+ cChar);
+ /*
+ * transmit character
+ */
+ outport_byte(&pNS16550Write->TransmitBuffer, cChar);
+ }
+
+ inport_byte(&pNS16550Read->InterruptId, ucInterruptId);
+ }
+ while((ucInterruptId&0xf)!=0x1);
+}
+
+static rtems_isr ns16550_isr(
+ rtems_vector_number vector
+)
+{
+ int minor;
+
+ for(minor=0;minor<Console_Port_Count;minor++)
+ {
+ if(vector==Console_Port_Tbl[minor].ulIntVector)
+ {
+ ns16550_process(minor);
+ }
+ }
+}
+
+/*
+ * ns16550_flush
+ */
+static int ns16550_flush(int major, int minor, void *arg)
+{
+ while(!Ring_buffer_Is_empty(&Console_Port_Data[minor].TxBuffer))
+ {
+ /*
+ * Yield while we wait
+ */
+ if(_System_state_Is_up(_System_state_Get()))
+ {
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+ }
+
+ ns16550_close(major, minor, arg);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * ns16550_initialize_interrupts
+ *
+ * This routine initializes the console's receive and transmit
+ * ring buffers and loads the appropriate vectors to handle the interrupts.
+ *
+ * Input parameters: NONE
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+
+static void ns16550_enable_interrupts(
+ int minor
+)
+{
+ PSP_WRITE_REGISTERS pNS16550Write;
+ unsigned8 ucDataByte;
+
+ pNS16550Write=(PSP_WRITE_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Enable interrupts
+ */
+ ucDataByte = SP_INT_RX_ENABLE | SP_INT_TX_ENABLE;
+ outport_byte(&pNS16550Write->InterruptEnable, ucDataByte);
+
+}
+
+static void ns16550_initialize_interrupts(int minor)
+{
+ ns16550_init(minor);
+
+ Ring_buffer_Initialize(&Console_Port_Data[minor].TxBuffer);
+
+ Console_Port_Data[minor].bActive = FALSE;
+
+ set_vector(ns16550_isr,
+ Console_Port_Tbl[minor].ulIntVector,
+ 1);
+
+ ns16550_enable_interrupts(minor);
+}
+
+/*
+ * ns16550_write_support_int
+ *
+ * Console Termios output entry point.
+ *
+ */
+static int ns16550_write_support_int(
+ int minor,
+ const char *buf,
+ int len)
+{
+ int i;
+ unsigned32 Irql;
+
+ for(i=0; i<len;)
+ {
+ if(Ring_buffer_Is_full(&Console_Port_Data[minor].TxBuffer))
+ {
+ if(!Console_Port_Data[minor].bActive)
+ {
+ /*
+ * Wake up the device
+ */
+ rtems_interrupt_disable(Irql);
+ Console_Port_Data[minor].bActive = TRUE;
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&ns16550_flow_RTSCTS)
+ {
+ ns16550_assert_RTS(minor);
+ }
+ ns16550_process(minor);
+ rtems_interrupt_enable(Irql);
+ }
+ else
+ {
+ /*
+ * Yield
+ */
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+
+ /*
+ * Wait for ring buffer to empty
+ */
+ continue;
+ }
+ else
+ {
+ Ring_buffer_Add_character(
+ &Console_Port_Data[minor].TxBuffer,
+ buf[i]);
+ i++;
+ }
+ }
+
+ /*
+ * Ensure that characters are on the way
+ */
+ if(!Console_Port_Data[minor].bActive)
+ {
+ /*
+ * Wake up the device
+ */
+ rtems_interrupt_disable(Irql);
+ Console_Port_Data[minor].bActive = TRUE;
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&ns16550_flow_RTSCTS)
+ {
+ ns16550_assert_RTS(minor);
+ }
+ ns16550_process(minor);
+ rtems_interrupt_enable(Irql);
+ }
+
+ return (len);
+}
+
+/*
+ * ns16550_write_support_polled
+ *
+ * Console Termios output entry point.
+ *
+ */
+static int ns16550_write_support_polled(
+ int minor,
+ const char *buf,
+ int len)
+{
+ int nwrite = 0;
+
+ /*
+ * poll each byte in the string out of the port.
+ */
+ while (nwrite < len)
+ {
+ /*
+ * transmit character
+ */
+ ns16550_write_polled(minor, *buf++);
+ nwrite++;
+ }
+
+ /*
+ * return the number of bytes written.
+ */
+ return nwrite;
+}
+
+/*
+ * ns16550_inbyte_nonblocking_polled
+ *
+ * Console Termios polling input entry point.
+ */
+
+static int ns16550_inbyte_nonblocking_polled(
+ int minor
+)
+{
+ PSP_READ_REGISTERS pNS16550Read;
+ unsigned char ucLineStatus;
+ char cChar;
+
+ pNS16550Read=(PSP_READ_REGISTERS)Console_Port_Tbl[minor].ulCtrlPort1;
+
+ inport_byte(&pNS16550Read->LineStatus, ucLineStatus);
+ if(ucLineStatus & SP_LSR_RDY)
+ {
+ inport_byte(&pNS16550Read->ReceiveBuffer, cChar);
+ return((int)cChar);
+ }
+ else
+ {
+ return(-1);
+ }
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.h
new file mode 100644
index 0000000000..e797ba2244
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550.h
@@ -0,0 +1,40 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#ifndef _NS16550_H_
+#define _NS16550_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * Driver function table
+ */
+extern console_fns ns16550_fns;
+extern console_fns ns16550_fns_polled;
+
+/*
+ * Flow control function tables
+ */
+extern console_flow ns16550_flow_RTSCTS;
+extern console_flow ns16550_flow_DTRCTS;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _NS16550_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550_p.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550_p.h
new file mode 100644
index 0000000000..7f7f51afa9
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550_p.h
@@ -0,0 +1,196 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#ifndef _NS16550_P_H_
+#define _NS16550_P_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+/*
+ * Define serial port read registers structure.
+ */
+
+typedef volatile struct _SP_READ_REGISTERS {
+ unsigned char ReceiveBuffer;
+ unsigned char InterruptEnable;
+ unsigned char InterruptId;
+ unsigned char LineControl;
+ unsigned char ModemControl;
+ unsigned char LineStatus;
+ unsigned char ModemStatus;
+ unsigned char ScratchPad;
+} SP_READ_REGISTERS, *PSP_READ_REGISTERS;
+
+/*
+ * Define serial port write registers structure.
+ */
+
+typedef volatile struct _SP_WRITE_REGISTERS {
+ unsigned char TransmitBuffer;
+ unsigned char InterruptEnable;
+ unsigned char FifoControl;
+ unsigned char LineControl;
+ unsigned char ModemControl;
+ unsigned char Reserved1;
+ unsigned char ModemStatus;
+ unsigned char ScratchPad;
+} SP_WRITE_REGISTERS, *PSP_WRITE_REGISTERS;
+
+/*
+ * Define serial port interrupt enable register structure.
+ */
+
+#define SP_INT_RX_ENABLE 0x01
+#define SP_INT_TX_ENABLE 0x02
+#define SP_INT_LS_ENABLE 0x04
+#define SP_INT_MS_ENABLE 0x08
+
+/*
+ * Define serial port interrupt id register structure.
+ */
+
+typedef struct _SP_INTERRUPT_ID {
+ unsigned char InterruptPending : 1;
+ unsigned char Identification : 3;
+ unsigned char Reserved1 : 2;
+ unsigned char FifoEnabled : 2;
+} SP_INTERRUPT_ID, *PSP_INTERRUPT_ID;
+
+/*
+ * Define serial port fifo control register structure.
+ */
+#define SP_FIFO_ENABLE 0x01
+#define SP_FIFO_RXRST 0x02
+#define SP_FIFO_TXRST 0x04
+#define SP_FIFO_DMA 0x08
+#define SP_FIFO_RXLEVEL 0xc0
+
+/*
+ * Define serial port line control register structure.
+ */
+#define SP_LINE_SIZE 0x03
+#define SP_LINE_STOP 0x04
+#define SP_LINE_PAR 0x08
+#define SP_LINE_ODD 0x10
+#define SP_LINE_STICK 0x20
+#define SP_LINE_BREAK 0x40
+#define SP_LINE_DLAB 0x80
+
+/*
+ * Line status register character size definitions.
+ */
+#define FIVE_BITS 0x0 /* five bits per character */
+#define SIX_BITS 0x1 /* six bits per character */
+#define SEVEN_BITS 0x2 /* seven bits per character */
+#define EIGHT_BITS 0x3 /* eight bits per character */
+
+/*
+ * Line speed divisor definition.
+ */
+#define NS16550_Baud(baud_rate) (115200/baud_rate)
+
+/*
+ * Define serial port modem control register structure.
+ */
+#define SP_MODEM_DTR 0x01
+#define SP_MODEM_RTS 0x02
+#define SP_MODEM_IRQ 0x08
+#define SP_MODEM_LOOP 0x10
+#define SP_MODEM_DIV4 0x80
+
+/*
+ * Define serial port line status register structure.
+ */
+#define SP_LSR_RDY 0x01
+#define SP_LSR_EOVRUN 0x02
+#define SP_LSR_EPAR 0x04
+#define SP_LSR_EFRAME 0x08
+#define SP_LSR_BREAK 0x10
+#define SP_LSR_THOLD 0x20
+#define SP_LSR_TX 0x40
+#define SP_LSR_EFIFO 0x80
+
+typedef struct _ns16550_context
+{
+ unsigned8 ucModemCtrl;
+} ns16550_context;
+
+/*
+ * Driver functions
+ */
+static boolean ns16550_probe(int minor);
+
+static void ns16550_init(int minor);
+
+static int ns16550_open(
+ int major,
+ int minor,
+ void * arg
+);
+
+static int ns16550_close(
+ int major,
+ int minor,
+ void * arg
+);
+
+static void ns16550_write_polled(
+ int minor,
+ char cChar
+);
+
+static void ns16550_assert_RTS(
+ int minor
+);
+
+static void ns16550_negate_RTS(
+ int minor
+);
+
+static void ns16550_assert_DTR(
+ int minor
+);
+
+static void ns16550_negate_DTR(
+ int minor
+);
+
+static void ns16550_initialize_interrupts(int minor);
+
+static int ns16550_flush(int major, int minor, void *arg);
+
+static int ns16550_write_support_int(
+ int minor,
+ const char *buf,
+ int len
+);
+
+static int ns16550_write_support_polled(
+ int minor,
+ const char *buf,
+ int len
+ );
+
+static int ns16550_inbyte_nonblocking_polled(
+ int minor
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _NS16550_P_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.c
new file mode 100644
index 0000000000..88cbde4bbe
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.c
@@ -0,0 +1,53 @@
+/* nc16550cfg.c
+ *
+ * This include file contains all console driver definations for the nc16550
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+
+unsigned8 Read_ns16550_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum
+)
+{
+ unsigned char *p = (unsigned char *)ulCtrlPort;
+ unsigned char ucData;
+
+ inport_byte( &p[ucRegNum], ucData );
+ return ucData;
+}
+
+void Write_ns16550_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum,
+ unsigned8 ucData
+)
+{
+ unsigned char *p = (unsigned char *)ulCtrlPort;
+
+ outport_byte( &p[ucRegNum], ucData );
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.h
new file mode 100644
index 0000000000..87235a80f2
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/ns16550cfg.h
@@ -0,0 +1,55 @@
+/* nc16550cfg.h
+ *
+ * This include file contains all console driver definations for the nc16550
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#ifndef __NS16550_CONFIG_H
+#define __NS16550_CONFIG_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * Board specific register access routines
+ */
+
+unsigned8 Read_ns16550_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum
+);
+
+void Write_ns16550_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum,
+ unsigned8 ucData
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga.c
new file mode 100644
index 0000000000..ed7a867d1d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga.c
@@ -0,0 +1,368 @@
+/*
+ * This file contains the TTY driver for VGA
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * This driver uses the termios pseudo driver.
+ */
+/*-------------------------------------------------------------------------+
+| (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>
+
+#include "vga_p.h"
+
+/*-------------------------------------------------------------------------+
+| Constants
++--------------------------------------------------------------------------*/
+#define DISPLAY_CELL_COUNT (VGA_NUM_ROWS * VGA_NUM_COLS)
+ /* Number of display cells. */
+#define TABSIZE 4 /* Number of spaces for TAB (\t) char. */
+#define WHITE 0x0007 /* White on Black background colour. */
+#define BLANK (WHITE | (' '<<8)) /* Blank character. */
+
+/*
+ * This is imported from i8042.c to provide flow control
+ */
+extern volatile boolean bScrollLock;
+
+/*-------------------------------------------------------------------------+
+| Global Variables
++--------------------------------------------------------------------------*/
+/* Physical address of start of video text memory. */
+static unsigned16 *videoRam = (unsigned16 *)VGA_FB;
+/* Pointer for current output position in display. */
+static unsigned16 *videoRamPtr = (unsigned16 *)VGA_FB;
+static unsigned8 videoRows = VGA_NUM_ROWS; /* Number of rows in display. */
+static unsigned8 videoCols = VGA_NUM_COLS; /* Number of columns in display. */
+static unsigned8 cursRow = 0; /* Current cursor row. */
+static 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(unsigned16 videoCursor)
+{
+ VGA_WRITE_CRTC(0x0e, (videoCursor >> 8) & 0xff);
+ VGA_WRITE_CRTC(0x0f, 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(unsigned8 lines)
+{
+ /* Number of blank display cells on bottom of window. */
+ unsigned16 blankCount;
+
+ /* Source and destination pointers for memory copy operations. */
+ unsigned16 *ptrDst, *ptrSrc;
+
+ if(lines<videoRows) /* Move window's contents up. */
+ {
+ /*
+ * Number of non-blank cells on upper part
+ * of display (total - blank).
+ */
+ unsigned16 nonBlankCount;
+
+ 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<<8) | 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 */
+
+/*
+ * Console Device Driver Entry Points
+ */
+void
+vga_write(
+ int minor,
+ char cChar)
+{
+ switch (cChar)
+ {
+ case '\b':
+ printBS();
+ break;
+ case '\t':
+ printHT();
+ break;
+ case '\n':
+ printLF();
+ break;
+ case '\r':
+ printCR();
+ break;
+ default:
+ printCHAR(cChar);
+ break;
+ }
+
+ setHardwareCursorPos(videoRamPtr - videoRam);
+} /* vga_write */
+
+/*
+ * vga_write_support
+ *
+ * Console Termios output entry point.
+ *
+ */
+int vga_write_support(
+ int minor,
+ const char *buf,
+ int len
+)
+{
+ int nwrite = 0;
+
+ while(bScrollLock)
+ {
+ /*
+ * The Scroll lock on the keyboard is active
+ */
+ /*
+ * Yield while we wait
+ */
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+
+ /*
+ * Write each byte in the string to the display
+ */
+ while (nwrite<len)
+ {
+ /*
+ * transmit character
+ */
+ vga_write(minor, *buf++);
+ nwrite++;
+ }
+
+ /*
+ * return the number of bytes written.
+ */
+ return nwrite;
+}
+
+boolean vga_probe(int minor)
+{
+ unsigned8 ucMiscIn;
+
+ /*
+ * Check for presence of VGA adaptor
+ */
+ inport_byte(0x3cc, ucMiscIn);
+ if(ucMiscIn!=0xff)
+ {
+ /*
+ * VGA device is present
+ */
+ return(TRUE);
+ }
+ return(FALSE);
+}
+
+void vga_init(int minor)
+{
+ scrollUp(videoRows); /* Clear entire screen */
+ setHardwareCursorPos(0); /* Cursor at upper left corner */
+ /*
+ * Enable the cursor
+ */
+ VGA_WRITE_CRTC(0x0a, 0x0e); /* Crt cursor start */
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga_p.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga_p.h
new file mode 100644
index 0000000000..591365a94f
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/vga_p.h
@@ -0,0 +1,70 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#ifndef _VGA_P_H_
+#define _VGA_P_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define VGA_FB ((unsigned32)PCI_MEM_BASE+0xb8000)
+#define VGA_NUM_ROWS 25
+#define VGA_NUM_COLS 80
+
+#define VGA_WRITE_SEQ(reg, val) \
+ outport_byte(0x3c4, reg); \
+ outport_byte(0x3c5, val)
+#define VGA_READ_SEQ(reg, val) \
+ outport_byte(0x3c4, reg); \
+ inport_byte(0x3c5, val)
+#define VGA_WRITE_CRTC(reg, val) \
+ outport_byte(0x3d4, reg); \
+ outport_byte(0x3d5, val)
+#define VGA_WRITE_GRA(reg, val) \
+ outport_byte(0x3ce, reg); \
+ outport_byte(0x3cf, val)
+#define VGA_WRITE_ATT(reg, val) \
+ { \
+ volatile unsigned8 ucDummy; \
+ inport_byte(0x3da, ucDummy); \
+ outport_byte(0x3c0, reg); \
+ outport_byte(0x3c0, val); \
+ }
+
+/*
+ * Exported functions
+ */
+extern boolean vga_probe(int minor);
+
+extern void vga_init(int minor);
+
+extern void vga_write(
+ int minor,
+ char cChar
+);
+
+extern int vga_write_support(
+ int minor,
+ const char *buf,
+ int len
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _VGA_P_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.c
new file mode 100644
index 0000000000..720117dc8d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.c
@@ -0,0 +1,917 @@
+/*
+ * This file contains the console driver chip level routines for the
+ * z85c30 chip.
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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.
+ *
+ * $Id:
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+#include <rtems/libio.h>
+#include <stdlib.h>
+
+#include "console.h"
+#include "z85c30_p.h"
+
+/*
+ * Flow control is only supported when using interrupts
+ */
+console_flow z85c30_flow_RTSCTS =
+{
+ z85c30_negate_RTS, /* deviceStopRemoteTx */
+ z85c30_assert_RTS /* deviceStartRemoteTx */
+};
+
+console_flow z85c30_flow_DTRCTS =
+{
+ z85c30_negate_DTR, /* deviceStopRemoteTx */
+ z85c30_assert_DTR /* deviceStartRemoteTx */
+};
+
+/*
+ * Exported driver function table
+ */
+console_fns z85c30_fns =
+{
+ z85c30_probe, /* deviceProbe */
+ z85c30_open, /* deviceFirstOpen */
+ z85c30_flush, /* deviceLastClose */
+ NULL, /* deviceRead */
+ z85c30_write_support_int, /* deviceWrite */
+ z85c30_initialize_interrupts, /* deviceInitialize */
+ z85c30_write_polled, /* deviceWritePolled */
+ FALSE, /* deviceOutputUsesInterrupts */
+};
+
+console_fns z85c30_fns_polled =
+{
+ z85c30_probe, /* deviceProbe */
+ z85c30_open, /* deviceFirstOpen */
+ z85c30_close, /* deviceLastClose */
+ z85c30_inbyte_nonblocking_polled, /* deviceRead */
+ z85c30_write_support_polled, /* deviceWrite */
+ z85c30_init, /* deviceInitialize */
+ z85c30_write_polled, /* deviceWritePolled */
+ FALSE, /* deviceOutputUsesInterrupts */
+};
+
+/*
+ * Read_85c30_register
+ *
+ * Read a Z85c30 register
+ */
+static unsigned8 Read_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum
+)
+{
+ unsigned8 ucData;
+
+ outport_byte(ulCtrlPort, ucRegNum);
+
+ inport_byte(ulCtrlPort, ucData);
+
+ return ucData;
+}
+
+/*
+ * Write_85c30_register
+ *
+ * Write a Z85c30 register
+ */
+static void Write_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum,
+ unsigned8 ucData
+)
+{
+ if(ucRegNum!=SCC_WR0_SEL_WR0)
+ {
+ outport_byte(ulCtrlPort, ucRegNum);
+ }
+ outport_byte(ulCtrlPort, ucData);
+}
+
+/*
+ * Read_85c30_data
+ *
+ * Read a Z85c30 data register
+ */
+static unsigned8 Read_85c30_data(
+ unsigned32 ulDataPort
+)
+{
+ unsigned8 ucData;
+
+ inport_byte(ulDataPort, ucData);
+
+ return ucData;
+}
+
+/*
+ * Write_85c30_data
+ *
+ * Write a Z85c30 data register
+ */
+static void Write_85c30_data(
+ unsigned32 ulDataPort,
+ unsigned8 ucData
+)
+{
+ outport_byte(ulDataPort, ucData);
+}
+
+/*
+ * z85c30_initialize_port
+ *
+ * initialize a z85c30 Port
+ */
+static void z85c30_initialize_port(
+ int minor
+)
+{
+ unsigned32 ulCtrlPort;
+ unsigned32 ulBaudDivisor;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Using register 4
+ * Set up the clock rate is 16 times the data
+ * rate, 8 bit sync char, 1 stop bit, no parity
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR4,
+ SCC_WR4_1_STOP |
+ SCC_WR4_16_CLOCK);
+
+ /*
+ * Set up for 8 bits/character on receive with
+ * receiver disable via register 3
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR3,
+ SCC_WR3_RX_8_BITS);
+
+ /*
+ * Set up for 8 bits/character on transmit
+ * with transmitter disable via register 5
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR5,
+ SCC_WR5_TX_8_BITS);
+
+ /*
+ * Clear misc control bits
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR10,
+ 0x00);
+
+ /*
+ * Setup the source of the receive and xmit
+ * clock as BRG output and the transmit clock
+ * as the output source for TRxC pin via register 11
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR11,
+ SCC_WR11_OUT_BR_GEN |
+ SCC_WR11_TRXC_OI |
+ SCC_WR11_TX_BR_GEN |
+ SCC_WR11_RX_BR_GEN);
+
+ ulBaudDivisor=Z85C30_Baud(
+ (unsigned32)Console_Port_Tbl[minor].pDeviceParams);
+ /*
+ * Setup the lower 8 bits time constants=1E.
+ * If the time constans=1E, then the desire
+ * baud rate will be equilvalent to 9600, via register 12.
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR12,
+ ulBaudDivisor&0xff);
+
+ /*
+ * using register 13
+ * Setup the upper 8 bits time constant
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR13,
+ (ulBaudDivisor>>8)&0xff);
+
+ /*
+ * Enable the baud rate generator enable with clock from the
+ * SCC's PCLK input via register 14.
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR14,
+ SCC_WR14_BR_EN |
+ SCC_WR14_BR_SRC |
+ SCC_WR14_NULL);
+
+ /*
+ * We are only interested in CTS state changes
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR15,
+ SCC_WR15_CTS_IE);
+
+ /*
+ * Reset errors
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_INT);
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_ERR_RST);
+
+ /*
+ * Enable the receiver via register 3
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR3,
+ SCC_WR3_RX_8_BITS |
+ SCC_WR3_RX_EN);
+
+ /*
+ * Enable the transmitter pins set via register 5.
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR5,
+ SCC_WR5_TX_8_BITS |
+ SCC_WR5_TX_EN);
+
+ /*
+ * Disable interrupts
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR1,
+ 0);
+
+ /*
+ * Reset TX CRC
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_TX_CRC);
+
+ /*
+ * Reset interrupts
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_INT);
+}
+
+static int z85c30_open(
+ int major,
+ int minor,
+ void * arg
+)
+{
+ /*
+ * Assert DTR
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_DTRCTS)
+ {
+ z85c30_assert_DTR(minor);
+ }
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+static int z85c30_close(
+ int major,
+ int minor,
+ void * arg
+)
+{
+ /*
+ * Negate DTR
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_DTRCTS)
+ {
+ z85c30_negate_DTR(minor);
+ }
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * z85c30_write_polled
+ *
+ * This routine transmits a character using polling.
+ */
+static void z85c30_write_polled(
+ int minor,
+ char cChar
+)
+{
+ volatile unsigned8 z85c30_status;
+ unsigned32 ulCtrlPort;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Wait for the Transmit buffer to indicate that it is empty.
+ */
+ z85c30_status=Read_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_RD0);
+ while(!Z85C30_Status_Is_TX_buffer_empty(z85c30_status))
+ {
+ /*
+ * Yield while we wait
+ */
+ if(_System_state_Is_up(_System_state_Get()))
+ {
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+ z85c30_status=Read_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_RD0);
+ }
+
+ /*
+ * Write the character.
+ */
+ Write_85c30_data(Console_Port_Tbl[minor].ulDataPort, cChar);
+}
+
+/*
+ * Console Device Driver Entry Points
+ */
+static boolean z85c30_probe(int minor)
+{
+ /*
+ * If the configuration dependant probe has located the device then
+ * assume it is there
+ */
+ return(TRUE);
+}
+
+static void z85c30_init(int minor)
+{
+ unsigned32 ulCtrlPort;
+ unsigned8 dummy;
+ z85c30_context *pz85c30Context;
+
+ pz85c30Context=(z85c30_context *)malloc(sizeof(z85c30_context));
+
+ Console_Port_Data[minor].pDeviceContext=(void *)pz85c30Context;
+ pz85c30Context->ucModemCtrl=SCC_WR5_TX_8_BITS | SCC_WR5_TX_EN;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+ if(ulCtrlPort==Console_Port_Tbl[minor].ulCtrlPort2)
+ {
+ /*
+ * This is channel A
+ */
+ /*
+ * Ensure port state machine is reset
+ */
+ inport_byte(ulCtrlPort, dummy);
+
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR9,
+ SCC_WR9_CH_A_RST);
+ }
+ else
+ {
+ /*
+ * This is channel B
+ */
+ /*
+ * Ensure port state machine is reset
+ */
+ inport_byte(ulCtrlPort, dummy);
+
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR9,
+ SCC_WR9_CH_B_RST);
+ }
+
+ z85c30_initialize_port(minor);
+}
+
+/*
+ * These routines provide control of the RTS and DTR lines
+ */
+/*
+ * z85c30_assert_RTS
+ */
+static void z85c30_assert_RTS(int minor)
+{
+ unsigned32 Irql;
+ z85c30_context *pz85c30Context;
+
+ pz85c30Context=(z85c30_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ /*
+ * Assert RTS
+ */
+ rtems_interrupt_disable(Irql);
+ pz85c30Context->ucModemCtrl|=SCC_WR5_RTS;
+ Write_85c30_register(
+ Console_Port_Tbl[minor].ulCtrlPort1,
+ SCC_WR0_SEL_WR5,
+ pz85c30Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * z85c30_negate_RTS
+ */
+static void z85c30_negate_RTS(int minor)
+{
+ unsigned32 Irql;
+ z85c30_context *pz85c30Context;
+
+ pz85c30Context=(z85c30_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ /*
+ * Negate RTS
+ */
+ rtems_interrupt_disable(Irql);
+ pz85c30Context->ucModemCtrl&=~SCC_WR5_RTS;
+ Write_85c30_register(
+ Console_Port_Tbl[minor].ulCtrlPort1,
+ SCC_WR0_SEL_WR5,
+ pz85c30Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * These flow control routines utilise a connection from the local DTR
+ * line to the remote CTS line
+ */
+/*
+ * z85c30_assert_DTR
+ */
+static void z85c30_assert_DTR(int minor)
+{
+ unsigned32 Irql;
+ z85c30_context *pz85c30Context;
+
+ pz85c30Context=(z85c30_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ /*
+ * Assert DTR
+ */
+ rtems_interrupt_disable(Irql);
+ pz85c30Context->ucModemCtrl|=SCC_WR5_DTR;
+ Write_85c30_register(
+ Console_Port_Tbl[minor].ulCtrlPort1,
+ SCC_WR0_SEL_WR5,
+ pz85c30Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * z85c30_negate_DTR
+ */
+static void z85c30_negate_DTR(int minor)
+{
+ unsigned32 Irql;
+ z85c30_context *pz85c30Context;
+
+ pz85c30Context=(z85c30_context *)
+ Console_Port_Data[minor].pDeviceContext;
+
+ /*
+ * Negate DTR
+ */
+ rtems_interrupt_disable(Irql);
+ pz85c30Context->ucModemCtrl&=~SCC_WR5_DTR;
+ Write_85c30_register(
+ Console_Port_Tbl[minor].ulCtrlPort1,
+ SCC_WR0_SEL_WR5,
+ pz85c30Context->ucModemCtrl);
+ rtems_interrupt_enable(Irql);
+}
+
+/*
+ * z85c30_isr
+ *
+ * This routine is the console interrupt handler for COM3 and COM4
+ *
+ * Input parameters:
+ * vector - vector number
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+
+static void z85c30_process(
+ int minor,
+ unsigned8 ucIntPend
+)
+{
+ unsigned32 ulCtrlPort, ulDataPort;
+ volatile unsigned8 z85c30_status;
+ char cChar;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+ ulDataPort=Console_Port_Tbl[minor].ulDataPort;
+
+ /*
+ * Deal with any received characters
+ */
+ while(ucIntPend&SCC_RR3_B_RX_IP)
+ {
+ z85c30_status=Read_85c30_register(ulCtrlPort, SCC_WR0_SEL_RD0);
+ if(!Z85C30_Status_Is_RX_character_available(z85c30_status))
+ {
+ break;
+ }
+
+ /*
+ * Return the character read.
+ */
+ cChar=Read_85c30_data(ulDataPort);
+
+ rtems_termios_enqueue_raw_characters(
+ Console_Port_Data[minor].termios_data,
+ &cChar,
+ 1);
+ }
+
+ while(TRUE)
+ {
+ z85c30_status=Read_85c30_register(ulCtrlPort, SCC_WR0_SEL_RD0);
+ if(!Z85C30_Status_Is_TX_buffer_empty(z85c30_status))
+ {
+ /*
+ * We'll get another interrupt when
+ * the transmitter holding reg. becomes
+ * free again and we are clear to send
+ */
+ break;
+ }
+
+ if(!Z85C30_Status_Is_CTS_asserted(z85c30_status))
+ {
+ /*
+ * We can't transmit yet
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_TX_INT);
+ /*
+ * The next state change of CTS will wake us up
+ */
+ break;
+ }
+
+ if(Ring_buffer_Is_empty(&Console_Port_Data[minor].TxBuffer))
+ {
+ Console_Port_Data[minor].bActive=FALSE;
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_RTSCTS)
+ {
+ z85c30_negate_RTS(minor);
+ }
+ /*
+ * There is no data to transmit
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_TX_INT);
+ break;
+ }
+
+ Ring_buffer_Remove_character(
+ &Console_Port_Data[minor].TxBuffer,
+ cChar);
+ /*
+ * transmit character
+ */
+ Write_85c30_data(ulDataPort, cChar);
+
+ /*
+ * Interrupt once FIFO has room
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_TX_INT);
+ break;
+ }
+
+ if(ucIntPend&SCC_RR3_B_EXT_IP)
+ {
+ /*
+ * Clear the external status interrupt
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_INT);
+ z85c30_status=Read_85c30_register(ulCtrlPort, SCC_WR0_SEL_RD0);
+ }
+
+ /*
+ * Reset interrupts
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_HI_IUS);
+}
+
+static rtems_isr z85c30_isr(
+ rtems_vector_number vector
+)
+{
+ int minor;
+ unsigned32 ulCtrlPort;
+ volatile unsigned8 ucIntPend;
+ volatile unsigned8 ucIntPendPort;
+
+ for(minor=0;minor<Console_Port_Count;minor++)
+ {
+ if(vector==Console_Port_Tbl[minor].ulIntVector)
+ {
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort2;
+ do
+ {
+ ucIntPend=Read_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_RD3);
+
+ /*
+ * If this is channel A select channel A status
+ */
+ if(ulCtrlPort==
+ Console_Port_Tbl[minor].ulCtrlPort1)
+ {
+ ucIntPendPort=ucIntPend>>3;
+ ucIntPendPort=ucIntPendPort&=7;
+ }
+ else
+ {
+ ucIntPendPort=ucIntPend&=7;
+ }
+
+ if(ucIntPendPort)
+ {
+ z85c30_process(minor, ucIntPendPort);
+ }
+ } while(ucIntPendPort);
+ }
+ }
+}
+
+/*
+ * z85c30_flush
+ */
+static int z85c30_flush(int major, int minor, void *arg)
+{
+ while(!Ring_buffer_Is_empty(&Console_Port_Data[minor].TxBuffer))
+ {
+ /*
+ * Yield while we wait
+ */
+ if(_System_state_Is_up(_System_state_Get()))
+ {
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+ }
+
+ z85c30_close(major, minor, arg);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * z85c30_initialize_interrupts
+ *
+ * This routine initializes the console's receive and transmit
+ * ring buffers and loads the appropriate vectors to handle the interrupts.
+ *
+ * Input parameters: NONE
+ *
+ * Output parameters: NONE
+ *
+ * Return values: NONE
+ */
+
+static void z85c30_enable_interrupts(
+ int minor
+)
+{
+ unsigned32 ulCtrlPort;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * Enable interrupts
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR1,
+ SCC_WR1_EXT_INT_EN |
+ SCC_WR1_TX_INT_EN |
+ SCC_WR1_INT_ALL_RX);
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR2,
+ 0);
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR9,
+ SCC_WR9_MIE);
+
+ /*
+ * Reset interrupts
+ */
+ Write_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_WR0,
+ SCC_WR0_RST_INT);
+}
+
+static void z85c30_initialize_interrupts(
+ int minor
+)
+{
+ z85c30_init(minor);
+
+ Ring_buffer_Initialize(&Console_Port_Data[minor].TxBuffer);
+
+ Console_Port_Data[minor].bActive=FALSE;
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_RTSCTS)
+ {
+ z85c30_negate_RTS(minor);
+ }
+
+ if(Console_Port_Tbl[minor].ulCtrlPort1==
+ Console_Port_Tbl[minor].ulCtrlPort2)
+ {
+ /*
+ * Only do this for Channel A
+ */
+ set_vector(z85c30_isr,
+ Console_Port_Tbl[minor].ulIntVector,
+ 1);
+ }
+
+ z85c30_enable_interrupts(minor);
+}
+
+/*
+ * z85c30_write_support_int
+ *
+ * Console Termios output entry point.
+ *
+ */
+static int z85c30_write_support_int(
+ int minor,
+ const char *buf,
+ int len)
+{
+ int i;
+ unsigned32 Irql;
+
+ for(i=0; i<len;)
+ {
+ if(Ring_buffer_Is_full(&Console_Port_Data[minor].TxBuffer))
+ {
+ if(!Console_Port_Data[minor].bActive)
+ {
+ /*
+ * Wake up the device
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_RTSCTS)
+ {
+ z85c30_assert_RTS(minor);
+ }
+ rtems_interrupt_disable(Irql);
+ Console_Port_Data[minor].bActive=TRUE;
+ z85c30_process(minor, SCC_RR3_B_TX_IP);
+ rtems_interrupt_enable(Irql);
+ }
+ else
+ {
+ /*
+ * Yield while we await an interrupt
+ */
+ rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
+ }
+
+ /*
+ * Wait for ring buffer to empty
+ */
+ continue;
+ }
+ else
+ {
+ Ring_buffer_Add_character(
+ &Console_Port_Data[minor].TxBuffer,
+ buf[i]);
+ i++;
+ }
+ }
+
+ /*
+ * Ensure that characters are on the way
+ */
+ if(!Console_Port_Data[minor].bActive)
+ {
+ /*
+ * Wake up the device
+ */
+ if(Console_Port_Tbl[minor].pDeviceFlow
+ !=&z85c30_flow_RTSCTS)
+ {
+ z85c30_assert_RTS(minor);
+ }
+ rtems_interrupt_disable(Irql);
+ Console_Port_Data[minor].bActive=TRUE;
+ z85c30_process(minor, SCC_RR3_B_TX_IP);
+ rtems_interrupt_enable(Irql);
+ }
+
+ return (len);
+}
+
+/*
+ * z85c30_inbyte_nonblocking_polled
+ *
+ * This routine polls for a character.
+ */
+static int z85c30_inbyte_nonblocking_polled(
+ int minor
+)
+{
+ volatile unsigned8 z85c30_status;
+ unsigned32 ulCtrlPort;
+
+ ulCtrlPort=Console_Port_Tbl[minor].ulCtrlPort1;
+
+ /*
+ * return -1 if a character is not available.
+ */
+ z85c30_status=Read_85c30_register(ulCtrlPort,
+ SCC_WR0_SEL_RD0);
+ if(!Z85C30_Status_Is_RX_character_available(z85c30_status))
+ {
+ return -1;
+ }
+
+ /*
+ * Return the character read.
+ */
+ return Read_85c30_data(Console_Port_Tbl[minor].ulDataPort);
+}
+
+/*
+ * z85c30_write_support_polled
+ *
+ * Console Termios output entry point.
+ *
+ */
+static int z85c30_write_support_polled(
+ int minor,
+ const char *buf,
+ int len)
+{
+ int nwrite=0;
+
+ /*
+ * poll each byte in the string out of the port.
+ */
+ while (nwrite < len)
+ {
+ /*
+ * transmit character
+ */
+ z85c30_write_polled(minor, *buf++);
+ nwrite++;
+ }
+
+ /*
+ * return the number of bytes written.
+ */
+ return nwrite;
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.h
new file mode 100644
index 0000000000..df05316347
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30.h
@@ -0,0 +1,52 @@
+/* z85c30.h
+ *
+ * This include file contains all console driver definations for the z85c30
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#ifndef __Z85C30_H
+#define __Z85C30_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * Driver function table
+ */
+extern console_fns z85c30_fns;
+extern console_fns z85c30_fns_polled;
+
+/*
+ * Flow control function tables
+ */
+extern console_flow z85c30_flow_RTSCTS;
+extern console_flow z85c30_flow_DTRCTS;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30_p.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30_p.h
new file mode 100644
index 0000000000..985c3b202b
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30_p.h
@@ -0,0 +1,385 @@
+/* z85c30_p.h
+ *
+ * This include file contains all private driver definations for the z85c30
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#ifndef __Z85C30_P_H
+#define __Z85C30_P_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* bit values for write register 0 */
+/* command register */
+
+#define SCC_WR0_SEL_WR0 0x00
+#define SCC_WR0_SEL_WR1 0x01
+#define SCC_WR0_SEL_WR2 0x02
+#define SCC_WR0_SEL_WR3 0x03
+#define SCC_WR0_SEL_WR4 0x04
+#define SCC_WR0_SEL_WR5 0x05
+#define SCC_WR0_SEL_WR6 0x06
+#define SCC_WR0_SEL_WR7 0x07
+#define SCC_WR0_SEL_WR8 0x08
+#define SCC_WR0_SEL_WR9 0x09
+#define SCC_WR0_SEL_WR10 0x0a
+#define SCC_WR0_SEL_WR11 0x0b
+#define SCC_WR0_SEL_WR12 0x0c
+#define SCC_WR0_SEL_WR13 0x0d
+#define SCC_WR0_SEL_WR14 0x0e
+#define SCC_WR0_SEL_WR15 0x0f
+#define SCC_WR0_SEL_RD0 0x00
+#define SCC_WR0_SEL_RD1 0x01
+#define SCC_WR0_SEL_RD2 0x02
+#define SCC_WR0_SEL_RD3 0x03
+#define SCC_WR0_SEL_RD4 0x04
+#define SCC_WR0_SEL_RD5 0x05
+#define SCC_WR0_SEL_RD6 0x06
+#define SCC_WR0_SEL_RD7 0x07
+#define SCC_WR0_SEL_RD8 0x08
+#define SCC_WR0_SEL_RD9 0x09
+#define SCC_WR0_SEL_RD10 0x0a
+#define SCC_WR0_SEL_RD11 0x0b
+#define SCC_WR0_SEL_RD12 0x0c
+#define SCC_WR0_SEL_RD13 0x0d
+#define SCC_WR0_SEL_RD14 0x0e
+#define SCC_WR0_SEL_RD15 0x0f
+#define SCC_WR0_NULL_CODE 0x00
+#define SCC_WR0_RST_INT 0x10
+#define SCC_WR0_SEND_ABORT 0x18
+#define SCC_WR0_EN_INT_RX 0x20
+#define SCC_WR0_RST_TX_INT 0x28
+#define SCC_WR0_ERR_RST 0x30
+#define SCC_WR0_RST_HI_IUS 0x38
+#define SCC_WR0_RST_RX_CRC 0x40
+#define SCC_WR0_RST_TX_CRC 0x80
+#define SCC_WR0_RST_TX_UND 0xc0
+
+/* write register 2 */
+/* interrupt vector */
+
+/* bit values for write register 1 */
+/* tx/rx interrupt and data transfer mode definition */
+
+#define SCC_WR1_EXT_INT_EN 0x01
+#define SCC_WR1_TX_INT_EN 0x02
+#define SCC_WR1_PARITY 0x04
+#define SCC_WR1_RX_INT_DIS 0x00
+#define SCC_WR1_RX_INT_FIR 0x08
+#define SCC_WR1_INT_ALL_RX 0x10
+#define SCC_WR1_RX_INT_SPE 0x18
+#define SCC_WR1_RDMA_RECTR 0x20
+#define SCC_WR1_RDMA_FUNC 0x40
+#define SCC_WR1_RDMA_EN 0x80
+
+/* bit values for write register 3 */
+/* receive parameters and control */
+
+#define SCC_WR3_RX_EN 0x01
+#define SCC_WR3_SYNC_CHAR 0x02
+#define SCC_WR3_ADR_SEARCH 0x04
+#define SCC_WR3_RX_CRC_EN 0x08
+#define SCC_WR3_ENTER_HUNT 0x10
+#define SCC_WR3_AUTO_EN 0x20
+#define SCC_WR3_RX_5_BITS 0x00
+#define SCC_WR3_RX_7_BITS 0x40
+#define SCC_WR3_RX_6_BITS 0x80
+#define SCC_WR3_RX_8_BITS 0xc0
+
+/* bit values for write register 4 */
+/* tx/rx misc parameters and modes */
+
+#define SCC_WR4_PAR_EN 0x01
+#define SCC_WR4_PAR_EVEN 0x02
+#define SCC_WR4_SYNC_EN 0x00
+#define SCC_WR4_1_STOP 0x04
+#define SCC_WR4_2_STOP 0x0c
+#define SCC_WR4_8_SYNC 0x00
+#define SCC_WR4_16_SYNC 0x10
+#define SCC_WR4_SDLC 0x20
+#define SCC_WR4_EXT_SYNC 0x30
+#define SCC_WR4_1_CLOCK 0x00
+#define SCC_WR4_16_CLOCK 0x40
+#define SCC_WR4_32_CLOCK 0x80
+#define SCC_WR4_64_CLOCK 0xc0
+
+/* bit values for write register 5 */
+/* transmit parameter and controls */
+
+#define SCC_WR5_TX_CRC_EN 0x01
+#define SCC_WR5_RTS 0x02
+#define SCC_WR5_SDLC 0x04
+#define SCC_WR5_TX_EN 0x08
+#define SCC_WR5_SEND_BRK 0x10
+
+#define SCC_WR5_TX_5_BITS 0x00
+#define SCC_WR5_TX_7_BITS 0x20
+#define SCC_WR5_TX_6_BITS 0x40
+#define SCC_WR5_TX_8_BITS 0x60
+#define SCC_WR5_DTR 0x80
+
+/* write register 6 */
+/* sync chars or sdlc address field */
+
+/* write register 7 */
+/* sync char or sdlc flag */
+
+/* write register 8 */
+/* transmit buffer */
+
+/* bit values for write register 9 */
+/* master interrupt control */
+
+#define SCC_WR9_VIS 0x01
+#define SCC_WR9_NV 0x02
+#define SCC_WR9_DLC 0x04
+#define SCC_WR9_MIE 0x08
+#define SCC_WR9_STATUS_HI 0x10
+#define SCC_WR9_NO_RST 0x00
+#define SCC_WR9_CH_B_RST 0x40
+#define SCC_WR9_CH_A_RST 0x80
+#define SCC_WR9_HDWR_RST 0xc0
+
+/* bit values for write register 10 */
+/* misc tx/rx control bits */
+
+#define SCC_WR10_6_BIT_SYNC 0x01
+#define SCC_WR10_LOOP_MODE 0x02
+#define SCC_WR10_ABORT_UND 0x04
+#define SCC_WR10_MARK_IDLE 0x08
+#define SCC_WR10_ACT_POLL 0x10
+#define SCC_WR10_NRZ 0x00
+#define SCC_WR10_NRZI 0x20
+#define SCC_WR10_FM1 0x40
+#define SCC_WR10_FM0 0x60
+#define SCC_WR10_CRC_PRESET 0x80
+
+/* bit values for write register 11 */
+/* clock mode control */
+
+#define SCC_WR11_OUT_XTAL 0x00
+#define SCC_WR11_OUT_TX_CLK 0x01
+#define SCC_WR11_OUT_BR_GEN 0x02
+#define SCC_WR11_OUT_DPLL 0x03
+#define SCC_WR11_TRXC_OI 0x04
+#define SCC_WR11_TX_RTXC 0x00
+#define SCC_WR11_TX_TRXC 0x08
+#define SCC_WR11_TX_BR_GEN 0x10
+#define SCC_WR11_TX_DPLL 0x18
+#define SCC_WR11_RX_RTXC 0x00
+#define SCC_WR11_RX_TRXC 0x20
+#define SCC_WR11_RX_BR_GEN 0x40
+#define SCC_WR11_RX_DPLL 0x60
+#define SCC_WR11_RTXC_XTAL 0x80
+
+/* write register 12 */
+/* lower byte of baud rate generator time constant */
+
+/* write register 13 */
+/* upper byte of baud rate generator time constant */
+
+/* bit values for write register 14 */
+/* misc control bits */
+
+#define SCC_WR14_BR_EN 0x01
+#define SCC_WR14_BR_SRC 0x02
+#define SCC_WR14_DTR_FUNC 0x04
+#define SCC_WR14_AUTO_ECHO 0x08
+#define SCC_WR14_LCL_LOOP 0x10
+#define SCC_WR14_NULL 0x00
+#define SCC_WR14_SEARCH 0x20
+#define SCC_WR14_RST_CLK 0x40
+#define SCC_WR14_DIS_DPLL 0x60
+#define SCC_WR14_SRC_BR 0x80
+#define SCC_WR14_SRC_RTXC 0xa0
+#define SCC_WR14_FM_MODE 0xc0
+#define SCC_WR14_NRZI 0xe0
+
+/* bit values for write register 15 */
+/* external/status interrupt control */
+
+#define SCC_WR15_ZERO_CNT 0x02
+#define SCC_WR15_CD_IE 0x08
+#define SCC_WR15_SYNC_IE 0x10
+#define SCC_WR15_CTS_IE 0x20
+#define SCC_WR15_TX_UND_IE 0x40
+#define SCC_WR15_BREAK_IE 0x80
+
+/* bit values for read register 0 */
+/* tx/rx buffer status and external status */
+
+#define SCC_RR0_RX_AVAIL 0x01
+#define SCC_RR0_ZERO_CNT 0x02
+#define SCC_RR0_TX_EMPTY 0x04
+#define SCC_RR0_CD 0x08
+#define SCC_RR0_SYNC 0x10
+#define SCC_RR0_CTS 0x20
+#define SCC_RR0_TX_UND 0x40
+#define SCC_RR0_BREAK 0x80
+
+/* bit values for read register 1 */
+
+#define SCC_RR1_ALL_SENT 0x01
+#define SCC_RR1_RES_CD_2 0x02
+#define SCC_RR1_RES_CD_1 0x01
+#define SCC_RR1_RES_CD_0 0x08
+#define SCC_RR1_PAR_ERR 0x10
+#define SCC_RR1_RX_OV_ERR 0x20
+#define SCC_RR1_CRC_ERR 0x40
+#define SCC_RR1_END_FRAME 0x80
+
+/* read register 2 */
+/* interrupt vector */
+
+/* bit values for read register 3 */
+/* interrupt pending register */
+
+#define SCC_RR3_B_EXT_IP 0x01
+#define SCC_RR3_B_TX_IP 0x02
+#define SCC_RR3_B_RX_IP 0x04
+#define SCC_RR3_A_EXT_IP 0x08
+#define SCC_RR3_A_TX_IP 0x10
+#define SCC_RR3_A_RX_IP 0x20
+
+/* read register 8 */
+/* receive data register */
+
+/* bit values for read register 10 */
+/* misc status bits */
+
+#define SCC_RR10_ON_LOOP 0x02
+#define SCC_RR10_LOOP_SEND 0x10
+#define SCC_RR10_2_CLK_MIS 0x40
+#define SCC_RR10_1_CLK_MIS 0x80
+
+/* read register 12 */
+/* lower byte of time constant */
+
+/* read register 13 */
+/* upper byte of time constant */
+
+/* bit values for read register 15 */
+/* external/status ie bits */
+
+#define SCC_RR15_ZERO_CNT 0x02
+#define SCC_RR15_CD_IE 0x08
+#define SCC_RR15_SYNC_IE 0x10
+#define SCC_RR15_CTS_IE 0x20
+#define SCC_RR15_TX_UND_IE 0x40
+#define SCC_RR15_BREAK_IE 0x80
+
+typedef struct _z85c30_context
+{
+ unsigned8 ucModemCtrl;
+} z85c30_context;
+
+/*
+ * The following macro calculates the Baud constant. For the Z85C30 chip.
+ *
+ * Note: baud constant = ((clock frequency / Clock_X) / (2 * Baud Rate)) - 2
+ * eg ((10,000,000 / 16) / (2 * Baud Rate)) - 2
+ */
+#define Z85C30_Baud( _baud_rate ) \
+ ( (Z85C30_CLOCK /( 16 * 2 * _baud_rate)) - 2)
+
+#define Z85C30_Status_Is_RX_character_available(_status) \
+ ((_status) & SCC_RR0_RX_AVAIL)
+
+#define Z85C30_Status_Is_TX_buffer_empty(_status) \
+ ((_status) & SCC_RR0_TX_EMPTY)
+
+#define Z85C30_Status_Is_CTS_asserted(_status) \
+ ((_status) & SCC_RR0_CTS)
+
+#define Z85C30_Status_Is_break_abort(_status) \
+ ((_status) & SCC_RR0_BREAK)
+
+/*
+ * Private routines
+ */
+static boolean z85c30_probe(int minor);
+
+static void z85c30_init(int minor);
+
+static int z85c30_open(
+ int major,
+ int minor,
+ void * arg
+);
+
+static int z85c30_close(
+ int major,
+ int minor,
+ void * arg
+);
+
+static void z85c30_write_polled(
+ int minor,
+ char cChar
+);
+
+static void z85c30_assert_RTS(
+ int minor
+);
+
+static void z85c30_negate_RTS(
+ int minor
+);
+
+static void z85c30_assert_DTR(
+ int minor
+);
+
+static void z85c30_negate_DTR(
+ int minor
+);
+
+static void z85c30_initialize_interrupts(int minor);
+
+static int z85c30_flush(int major, int minor, void *arg);
+
+static int z85c30_write_support_int(
+ int minor,
+ const char *buf,
+ int len
+);
+
+static int z85c30_write_support_polled(
+ int minor,
+ const char *buf,
+ int len
+);
+
+static int z85c30_inbyte_nonblocking_polled(
+ int minor
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.c b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.c
new file mode 100644
index 0000000000..3a1a98c720
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.c
@@ -0,0 +1,96 @@
+/*
+ * This file contains the console driver chip level routines for the
+ * z85c30 chip.
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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.
+ *
+ * $Id$
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+
+/*
+ * Read_85c30_register
+ *
+ * Read a Z85c30 register
+ */
+
+unsigned8 Read_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum
+)
+{
+ unsigned8 ucData;
+
+ outport_byte(ulCtrlPort, ucRegNum);
+ inport_byte(ulCtrlPort, ucData);
+ return ucData;
+}
+
+/*
+ * Write_85c30_register
+ *
+ * Write a Z85c30 register
+ */
+
+void Write_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum,
+ unsigned8 ucData
+)
+{
+ if(ucRegNum) {
+ outport_byte(ulCtrlPort, ucRegNum);
+ }
+ outport_byte(ulCtrlPort, ucData);
+}
+
+/*
+ * Read_85c30_data
+ *
+ * Read a Z85c30 data register
+ */
+
+unsigned8 Read_85c30_data(
+ unsigned32 ulDataPort
+)
+{
+ unsigned8 ucData;
+
+ inport_byte(ulDataPort, ucData);
+ return ucData;
+}
+
+/*
+ * Write_85c30_data
+ *
+ * Write a Z85c30 data register
+ */
+
+void Write_85c30_data(
+ unsigned32 ulDataPort,
+ unsigned8 ucData
+)
+{
+ outport_byte(ulDataPort, ucData);
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.h b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.h
new file mode 100644
index 0000000000..3dfb96e048
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/console/z85c30cfg.h
@@ -0,0 +1,64 @@
+/* z85c30cfg.h
+ *
+ * This include file contains all console driver definations for the z85c30
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#ifndef __Z85C30_CONFIG_H
+#define __Z85C30_CONFIG_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * Board specific register access routines
+ */
+
+unsigned8 Read_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum
+);
+
+void Write_85c30_register(
+ unsigned32 ulCtrlPort,
+ unsigned8 ucRegNum,
+ unsigned8 ucData
+);
+
+unsigned8 Read_85c30_data(
+ unsigned32 ulDataPort
+);
+
+void Write_85c30_data(
+ unsigned32 ulDataPort,
+ unsigned8 ucData
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/include/Makefile.in
new file mode 100644
index 0000000000..011a5629e2
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/Makefile.in
@@ -0,0 +1,36 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+H_FILES = $(srcdir)/bsp.h $(srcdir)/coverhd.h $(srcdir)/chain.h \
+ $(srcdir)/tod.h $(srcdir)/nvram.h $(srcdir)/pci.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.
+#
+# If you add equate files, don't forget to uncomment the install line
+# below.
+#
+
+EQ_FILES =
+
+SRCS=$(H_FILES) $(EQ_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+CLEAN_ADDITIONS +=
+CLOBBER_ADDITIONS +=
+
+all: $(SRCS)
+ $(INSTALL) -m 444 $(H_FILES) $(PROJECT_INCLUDE)
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/bsp.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/bsp.h
new file mode 100644
index 0000000000..98fc0781bf
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/bsp.h
@@ -0,0 +1,465 @@
+/* bsp.h
+ *
+ * This include file contains all board IO definitions.
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http:www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#ifndef __BSP_h
+#define __BSP_h
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* Define processor identification. */
+
+#define MPC601 1
+#define MPC603 3
+#define MPC604 4
+#define MPC603e 6
+#define MPC603ev 7
+#define MPC604e 9
+
+#ifdef ASM
+/* Definition of where to store registers in alignment handler */
+#define ALIGN_REGS 0x0140
+
+/* BAT register definitions for the MPC603 and MPC604. */
+/* Define bit fields for upper MPC603/4 BAT registers. */
+
+#define BEPI_FIELD_60X 0xFFFE0000
+#define VALID_SUPERVISOR 0x2
+#define VALID_PROBLEM 0x1
+#define KEY_USER_60X 0x1
+#define BL_128K 0x0
+#define BL_256K (0x1<2)
+#define BL_512K (0x3<2)
+#define BL_1M (0x7<2)
+#define BL_2M (0xF<2)
+#define BL_4M (0x1F<2)
+#define BL_8M (0x3F<2)
+#define BL_16M (0x7F<2)
+#define BL_32M (0xFF<2)
+#define BL_64M (0x1FF<2)
+#define BL_128M (0x3FF<2)
+#define BL_256M (0x7FF<2)
+
+
+/* Define bit fields for lower MPC603/4 BAT registers. */
+
+#define BRPN_FIELD_60X 0xFFFE0000
+
+/* Common defines for BAT registers. */
+/* Depending on the processor, the following may be in the upper */
+/* and lower BAT register. */
+
+#define WRITE_THRU 0x40
+#define WRITE_BK 0x0
+#define COHERE_EN 0x10
+#define COHERE_DIS 0x0
+#define CACHE_DIS 0x20
+#define CACHE_EN 0x0
+#define GUARDED_EN 0x8
+#define GUARDED_DIS 0x0
+#define PP_00 0x0
+#define PP_01 0x1
+#define PP_10 0x2
+#define PP_11 0x3
+
+/* HID0 definitions for MPC603 and MPC604 */
+#define HID0 0x3f0 /* HID0 Special Purpose Register # */
+/* HID1 definitions for MPC603e and MPC604e */
+#define HID1 0x3f1 /* HID1 Special Purpose Register # */
+
+#define H0_603_ICFI 0x0800 /* HID0 I-Cache Flash Invalidate */
+#define H0_603_DCI 0x0400 /* HID0 D-Cache Flash Invalidate */
+
+#define H0_60X_ICE 0x8000 /* HID0 I-Cache Enable */
+#define H0_60X_DCE 0x4000 /* HID0 D-Cache Enable */
+
+#define H0_604_BHTE 0x0004 /* HID0 Branch History Table enable */
+#define H0_604_SIED 0x0080 /* HID0 Serial Instruction Execution */
+#define H0_604_ICIA 0x0800 /* HID0 I-Cache Invalidate All */
+#define H0_604_DCIA 0x0400 /* HID0 D-Cache Invalidate All */
+
+#define BAT0U 528
+#define BAT0L 529
+#define BAT1U 530
+#define BAT1L 531
+#define BAT2U 532
+#define BAT2L 533
+#define BAT3U 534
+#define BAT3L 535
+#define SPRG0 272
+#define SPRG1 273
+
+/* MSR bit settings */
+#define MSR_LE 0x0001
+#define MSR_RI 0x0002
+#define MSR_DR 0x0010
+#define MSR_IR 0x0020
+#define MSR_IP 0x0040
+#define MSR_FE1 0x0100
+#define MSR_BE 0x0200
+#define MSR_SE 0x0400
+#define MSR_FE0 0x0800
+#define MSR_ME 0x1000
+#define MSR_FP 0x2000
+#define MSR_PR 0x4000
+#define MSR_EE 0x8000
+#define MSR_ILE 0x0001 /* Upper 16 bits */
+#define MSR_POW 0x0004 /* Upper 16 bits */
+#else
+#include <rtems.h>
+#include <console.h>
+#include <clockdrv.h>
+#include <iosupp.h>
+#include <tod.h>
+#include <nvram.h>
+
+/*
+ * PPCn_60x Interupt Definations.
+ */
+#define PPCN_60X_8259_IRQ_BASE ( PPC_IRQ_LAST + 1 )
+
+/*
+ * 8259 IRQ definations.
+ */
+#define PPCN_60X_IRQ_SYS_TIMER (PPCN_60X_8259_IRQ_BASE + 0)
+#define PPCN_60X_IRQ_KBD (PPCN_60X_8259_IRQ_BASE + 1)
+#define PPCN_60X_IRQ_COM2 (PPCN_60X_8259_IRQ_BASE + 3)
+#define PPCN_60X_IRQ_COM1 (PPCN_60X_8259_IRQ_BASE + 4)
+#define PPCN_60X_IRQ_CIO (PPCN_60X_8259_IRQ_BASE + 5)
+#define PPCN_60X_IRQ_FDC (PPCN_60X_8259_IRQ_BASE + 6)
+#define PPCN_60X_IRQ_LPT (PPCN_60X_8259_IRQ_BASE + 7)
+#define PPCN_60X_IRQ_RTC (PPCN_60X_8259_IRQ_BASE + 8)
+#define PPCN_60X_IRQ_COM3_4 (PPCN_60X_8259_IRQ_BASE + 10)
+#define PPCN_60X_IRQ_MSE (PPCN_60X_8259_IRQ_BASE + 12)
+#define PPCN_60X_IRQ_SCSI (PPCN_60X_8259_IRQ_BASE + 13)
+
+/*
+ * PCI interrupts as read from line register map directly to
+ * ISA interrupt lines 9, 11, 14 and 15.
+ */
+#define PPCN_60X_IRQ_PCI(n) (PPCN_60X_8259_IRQ_BASE + (n))
+
+#define MAX_BOARD_IRQS (PPCN_60X_8259_IRQ_BASE + 15)
+
+#define ISA8259_M_CTRL 0x20
+#define ISA8259_S_CTRL 0xa0
+#define ISA8259_M_MASK 0x21
+#define ISA8259_S_MASK 0xa1
+#define ISA8259_M_ELCR 0x4d0
+#define ISA8259_S_ELCR 0x4d1
+
+#define ELCRS_INT15_LVL 0x80
+#define ELCRS_INT14_LVL 0x40
+#define ELCRS_INT12_LVL 0x10
+#define ELCRS_INT11_LVL 0x08
+#define ELCRS_INT10_LVL 0x04
+#define ELCRS_INT9_LVL 0x02
+#define ELCRS_INT8_LVL 0x01
+#define ELCRM_INT7_LVL 0x80
+#define ELCRM_INT5_LVL 0x20
+
+
+#define NONSPECIFIC_EOI 0x20
+
+extern void En_Ext_Interrupt(int level);
+extern void Dis_Ext_Interrupt(int level);
+
+#define IRQ_VECTOR_BASE 0xbffffff0
+
+/*
+ * i8042 addresses
+ */
+#define I8042_DATA 0x60
+#define I8042_CS 0x64
+
+/*
+ * ns16550 addresses
+ */
+#define NS16550_PORT_A 0x3f8
+#define NS16550_PORT_B 0x2f8
+
+/*
+ * z85c30 addresses
+ */
+#define Z85C30_CTRL_B 0x840
+#define Z85C30_DATA_B 0x841
+#define Z85C30_CTRL_A 0x842
+#define Z85C30_DATA_A 0x843
+
+/*
+ * Z85C30 Definations for the 422 interface.
+ */
+#define Z85C30_CLOCK 14745600
+
+#define PCI_SYS_MEM_BASE 0x80000000
+#define PCI_MEM_BASE 0xc0000000
+#define PCI_IO_BASE 0x80000000
+
+#define EIEIO asm volatile("eieio")
+
+/*
+ * As ports are all little endian we will perform swaps here on 16 and 32
+ * bit transfers
+ */
+extern unsigned16 Swap16(unsigned16 usVal);
+extern unsigned32 Swap32(unsigned32 ulVal);
+
+#define outport_byte(port, val) \
+ EIEIO; \
+ *(volatile unsigned8 *)(PCI_IO_BASE+ \
+ (unsigned long)(port))=(val)
+
+#define outport_16(port, val) \
+ EIEIO; \
+ *(volatile unsigned16 *)(PCI_IO_BASE+ \
+ (unsigned long)(port))=Swap16(val)
+
+#define outport_32(port, val) \
+ EIEIO; \
+ *(volatile unsigned32 *)(PCI_IO_BASE+ \
+ (unsigned long)(port))=Swap32(val)
+
+#define inport_byte(port, val) \
+ EIEIO; \
+ (val)=*(volatile unsigned8 *)(PCI_IO_BASE+ \
+ (unsigned long)(port))
+
+#define inport_16(port, val) \
+ EIEIO; \
+ (val)=Swap16(*(volatile unsigned16 *)(PCI_IO_BASE+ \
+ (unsigned long)(port)))
+
+#define inport_32(port, val) \
+ EIEIO; \
+ (val)=Swap32(*(volatile unsigned32 *)(PCI_IO_BASE+ \
+ (unsigned long)(port)))
+
+/*
+ * System Planar Board Registers
+ */
+typedef volatile struct _PLANARREGISTERS{
+ unsigned8 Reserved0[0x803]; /* Offset 0x000 */
+ unsigned8 SimmId; /* Offset 0x803 */
+ unsigned8 SimmPresent; /* Offset 0x804 */
+ unsigned8 Reserved1[3];
+ unsigned8 HardfileLight; /* Offset 0x808 */
+ unsigned8 Reserved2[3];
+ unsigned8 EquipmentPresent1; /* Offset 0x80C */
+ unsigned8 Reserved3;
+ unsigned8 EquipmentPresent2; /* Offset 0x80e */
+ unsigned8 Reserved4;
+ unsigned8 PasswordProtect1; /* Offset 0x810 */
+ unsigned8 Reserved5;
+ unsigned8 PasswordProtect2; /* Offset 0x812 */
+ unsigned8 Reserved6;
+ unsigned8 L2Flush; /* Offset 0x814 */
+ unsigned8 Reserved7[3];
+ unsigned8 Keylock; /* Offset 0x818 */
+ unsigned8 Reserved8[0x3c];
+ unsigned8 BoardRevision; /* Offset 0x854 */
+ unsigned8 Reserved9[0xf];
+ unsigned8 BoardID; /* Offset 0x864 */
+ unsigned8 Reserved10;
+ unsigned8 MotherboardMemoryType; /* Offset 0x866 */
+ unsigned8 Reserved11;
+ unsigned8 MezzanineMemoryType; /* Offset 0x868 */
+} PLANARREGISTERS, *PPLANARREGISTERS;
+
+extern unsigned char ucSystemType;
+extern unsigned char ucBoardRevMaj;
+extern unsigned char ucBoardRevMin;
+extern unsigned long ulMemorySize;
+extern unsigned long ulCpuBusClock;
+
+#define SYS_TYPE_PPC1 0
+#define SYS_TYPE_PPC2 1
+#define SYS_TYPE_PPC1a 2
+#define SYS_TYPE_PPC2a 3
+#define SYS_TYPE_PPC4 4
+
+/*
+ * PCI initialisation
+ */
+void InitializePCI(void);
+
+/*
+ * VME initiaisation
+ */
+void InitializeUniverse();
+
+/*
+ * RTC initialisation
+ */
+void InitializeRTC(void);
+
+/*
+ * NvRAM initialisation
+ */
+void InitializeNvRAM(void);
+
+/*
+ * BSP_TIMER_AVG_OVERHEAD and BSP_TIMER_LEAST_VALID for the shared timer
+ * driver.
+ */
+
+#define BSP_TIMER_AVG_OVERHEAD 4 /* It typically takes xx clicks */
+ /* to start/stop the timer. */
+#define BSP_TIMER_LEAST_VALID 1 /* Don't trust a value lower than this */
+
+/*
+ * Convert decrement value to tenths of microsecnds (used by
+ * shared timer driver).
+ *
+ * + There are 4 bus cycles per click
+ * + We return value in 1/10 microsecond units.
+ * Modified following equation to integer equation to remove
+ * floating point math.
+ * (int) ((float)(_value) / ((66.67 * 0.1) / 4.0))
+ */
+
+#define BSP_Convert_decrementer( _value ) \
+ (int) (((_value) * 4000) / (ulCpuBusClock/10000))
+
+/*
+ * 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 */
+
+/*
+ * Stuff for Time Test 27
+ */
+
+#define MUST_WAIT_FOR_INTERRUPT 1
+
+#define Install_tm27_vector( _handler ) \
+ set_vector( (_handler), PPC_IRQ_DECREMENTER, 1 )
+
+#define Cause_tm27_intr() \
+ do { \
+ unsigned32 _clicks = 8; \
+ asm volatile( "mtdec %0" : "=r" ((_clicks)) : "r" ((_clicks)) ); \
+ } while (0)
+
+
+#define Clear_tm27_intr() \
+ do { \
+ unsigned32 _clicks = 0xffffffff; \
+ asm volatile( "mtdec %0" : "=r" ((_clicks)) : "r" ((_clicks)) ); \
+ } while (0)
+
+#define Lower_tm27_intr() \
+ do { \
+ unsigned32 _msr = 0; \
+ _ISR_Set_level( 0 ); \
+ asm volatile( "mfmsr %0 ;" : "=r" (_msr) : "r" (_msr) ); \
+ _msr |= 0x8002; \
+ asm volatile( "mtmsr %0 ;" : "=r" (_msr) : "r" (_msr) ); \
+ } while (0)
+
+
+/* Constants */
+
+/*
+ * Device Driver Table Entries
+ */
+
+/*
+ * NOTE: Use the standard Console driver entry
+ */
+
+/*
+ * NOTE: Use the standard Clock driver entry
+ */
+
+/*
+ * How many libio files we want
+ */
+
+#define BSP_LIBIO_MAX_FDS 20
+
+/* functions */
+
+void bsp_start( void );
+
+void bsp_cleanup( void );
+
+rtems_isr_entry set_vector( /* returns old vector */
+ rtems_isr_entry handler, /* isr routine */
+ rtems_vector_number vector, /* vector number */
+ int type /* RTEMS or RAW intr */
+);
+
+/*
+ * spurious.c
+ */
+rtems_isr bsp_stub_handler(
+ rtems_vector_number trap
+);
+rtems_isr bsp_spurious_handler(
+ rtems_vector_number trap
+);
+void bsp_spurious_initialize();
+
+/*
+ * genvec.c
+ */
+void set_EE_vector(
+ rtems_isr_entry handler, /* isr routine */
+ rtems_vector_number vector /* vector number */
+);
+void initialize_external_exception_vector();
+
+/*
+ * console.c
+ */
+void DEBUG_puts( char *string );
+void DEBUG_puth( unsigned32 ulHexNum );
+
+void BSP_fatal_return( void );
+
+extern rtems_configuration_table BSP_Configuration; /* owned by BSP */
+
+extern rtems_cpu_table Cpu_table; /* owned by BSP */
+
+extern unsigned32 bsp_isr_level;
+
+#endif /* ASM */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+/* end of include file */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/chain.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/chain.h
new file mode 100644
index 0000000000..98cf2b1a86
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/chain.h
@@ -0,0 +1,362 @@
+/* chain.h
+ *
+ * This include file contains all the constants and structures associated
+ * with doubly linked chains. This file actually just provides an
+ * interface to the chain object in rtems.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $ld:
+ */
+
+#ifndef __CHAIN_h
+#define __CHAIN_h
+
+#include <rtems.h>
+
+/*
+ * Chain_Initialize
+ *
+ * This routine initializes the_chain structure to manage the
+ * contiguous array of number_nodes nodes which starts at
+ * starting_address. Each node is of node_size bytes.
+ *
+ * Chain_Control *the_chain, * IN *
+ * void *starting_address, * IN *
+ * rtems_unsigned32 number_nodes, * IN *
+ * rtems_unsigned32 node_size * IN *
+ */
+
+#define Chain_Initialize( the_chain, starting_address, \
+ number_nodes, node_size ) \
+ _Chain_Initialize( the_chain, starting_address, \
+ number_nodes, node_size ) \
+
+
+/*
+ * Chain_Initialize_empty
+ *
+ * This routine initializes the specified chain to contain zero nodes.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Initialize_empty( the_chain ) \
+ _Chain_Initialize_empty( the_chain )
+
+
+/*
+ * Chain_Are_nodes_equal
+ *
+ * This function returns TRUE if LEFT and RIGHT are equal,
+ * and FALSE otherwise.
+ *
+ * Chain_Node *left, * IN *
+ * Chain_Node *right * IN *
+ */
+
+#define Chain_Are_nodes_equal( left, right ) \
+ _Chain_Are_nodes_equal( left, right )
+
+
+/*
+ * Chain_Extract_unprotected
+ *
+ * This routine extracts the_node from the chain on which it resides.
+ * It does NOT disable interrupts to insure the atomicity of the
+ * extract operation.
+ *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Extract_unprotected( the_node ) \
+ _Chain_Extract_unprotected( the_node )
+
+
+/*
+ * Chain_Extract
+ *
+ * This routine extracts the_node from the chain on which it resides.
+ * It disables interrupts to insure the atomicity of the
+ * extract operation.
+ *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Extract( the_node ) \
+ _Chain_Extract( the_node )
+
+
+/*
+ * Chain_Get_unprotected
+ *
+ * This function removes the first node from the_chain and returns
+ * a pointer to that node. If the_chain is empty, then NULL is returned.
+ * It does NOT disable interrupts to insure the atomicity of the
+ * get operation.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Get_unprotected( the_chain ) \
+ _Chain_Get_unprotected( the_chain )
+
+
+/*
+ * Chain_Get
+ *
+ * This function removes the first node from the_chain and returns
+ * a pointer to that node. If the_chain is empty, then NULL is returned.
+ * It disables interrupts to insure the atomicity of the
+ * get operation.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Get( the_chain ) \
+ _Chain_Get( the_chain )
+
+
+/*
+ * Chain_Get_first_unprotected
+ *
+ * This function removes the first node from the_chain and returns
+ * a pointer to that node. It does NOT disable interrupts to insure
+ * the atomicity of the get operation.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Get_first_unprotected( the_chain ) \
+ _Chain_Get_first_unprotected( the_chain )
+
+
+/*
+ * Chain_Insert_unprotected
+ *
+ * This routine inserts the_node on a chain immediately following
+ * after_node. It does NOT disable interrupts to insure the atomicity
+ * of the extract operation.
+ *
+ * Chain_Node *after_node, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Insert_unprotected( after_node, the_node ) \
+ _Chain_Insert_unprotected( after_node, the_node )
+
+
+/*
+ * Chain_Insert
+ *
+ * This routine inserts the_node on a chain immediately following
+ * after_node. It disables interrupts to insure the atomicity
+ * of the extract operation.
+ *
+ * Chain_Node *after_node, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Insert( after_node, the_node ) \
+ _Chain_Insert( after_node, the_node )
+
+
+/*
+ * Chain_Append_unprotected
+ *
+ * This routine appends the_node onto the end of the_chain.
+ * It does NOT disable interrupts to insure the atomicity of the
+ * append operation.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Append_unprotected( the_chain, the_node ) \
+ _Chain_Append_unprotected( the_chain, the_node )
+
+
+/*
+ * Chain_Append
+ *
+ * This routine appends the_node onto the end of the_chain.
+ * It disables interrupts to insure the atomicity of the
+ * append operation.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Append( the_chain, the_node ) \
+ _Chain_Append( the_chain, the_node )
+
+
+/*
+ * Chain_Prepend_unprotected
+ *
+ * This routine prepends the_node onto the front of the_chain.
+ * It does NOT disable interrupts to insure the atomicity of the
+ * prepend operation.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Prepend_unprotected( the_chain, the_node ) \
+ _Chain_Prepend_unprotected( the_chain, the_node )
+
+
+/*
+ * Chain_Prepend
+ *
+ * This routine prepends the_node onto the front of the_chain.
+ * It disables interrupts to insure the atomicity of the
+ * prepend operation.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Prepend( the_chain, the_node ) \
+ _Chain_Prepend( the_chain, the_node )
+
+
+/*
+ * Chain_Head
+ *
+ * This function returns a pointer to the first node on the chain.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Head( the_chain ) \
+ _Chain_Head( the_chain )
+
+
+/*
+ * Chain_Tail
+ *
+ * This function returns a pointer to the last node on the chain.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Tail( the_chain ) \
+ _Chain_Tail( the_chain )
+
+
+/*
+ * Chain_Is_head
+ *
+ * This function returns TRUE if the_node is the head of the_chain and
+ * FALSE otherwise.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Is_head( the_chain, the_node ) \
+ _Chain_Is_head( the_chain, the_node )
+
+
+/*
+ * Chain_Is_tail
+ *
+ * This function returns TRUE if the_node is the tail of the_chain and
+ * FALSE otherwise.
+ *
+ * Chain_Control *the_chain, * IN *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Is_tail( the_chain, the_node ) \
+ _Chain_Is_tail( the_chain, the_node )
+
+
+/*
+ * Chain_Is_first
+ *
+ * This function returns TRUE if the_node is the first node on a chain and
+ * FALSE otherwise.
+ *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Is_first( the_node ) \
+ _Chain_Is_first( the_node )
+
+
+/*
+ * Chain_Is_last
+ *
+ * This function returns TRUE if the_node is the last node on a chain and
+ * FALSE otherwise.
+ *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Is_last( the_node ) \
+ _Chain_Is_last( the_node )
+
+
+/*
+ * Chain_Is_empty
+ *
+ * This function returns TRUE if there are no nodes on the_chain and
+ * FALSE otherwise.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Is_empty( the_chain ) \
+ _Chain_Is_empty( the_chain )
+
+
+/*
+ * Chain_Has_only_one_node
+ *
+ * This function returns TRUE if there is only one node on the_chain and
+ * FALSE otherwise.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Has_only_one_node( the_chain ) \
+ _Chain_Has_only_one_node( the_chain )
+
+
+/*
+ * Chain_Is_null
+ *
+ * This function returns TRUE if the_chain is NULL and FALSE otherwise.
+ *
+ * Chain_Control *the_chain * IN *
+ */
+
+#define Chain_Is_null( the_chain ) \
+ _Chain_Is_null( the_chain )
+
+
+/*
+ * Chain_Is_null_node
+ *
+ * This function returns TRUE if the_node is NULL and FALSE otherwise.
+ *
+ * Chain_Node *the_node * IN *
+ */
+
+#define Chain_Is_null_node( the_node ) \
+ _Chain_Is_null_node( the_node )
+
+
+#undef __RTEMS_APPLICATION__
+#include <rtems/score/chain.inl>
+#define __RTEMS_APPLICATION__
+#endif
+/* end of include file */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/coverhd.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/coverhd.h
new file mode 100644
index 0000000000..340c5ca16d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/coverhd.h
@@ -0,0 +1,119 @@
+/* coverhd.h
+ *
+ * This include file has defines to represent the overhead associated
+ * with calling a particular directive from C. These are used in the
+ * Timing Test Suite to ignore the overhead required to pass arguments
+ * to directives. On some CPUs and/or target boards, this overhead
+ * is significant and makes it difficult to distinguish internal
+ * RTEMS execution time from that used to call the directive.
+ * This file should be updated after running the C overhead timing
+ * test. Once this update has been performed, the RTEMS Time Test
+ * Suite should be rebuilt to account for these overhead times in the
+ * timing results.
+ *
+ * NOTE: If these are all zero, then the times reported include
+ * calling overhead including passing of arguments.
+ *
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#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_IDENT 0
+#define CALLING_OVERHEAD_SEMAPHORE_DELETE 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 */
+
+
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/extisrdrv.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/extisrdrv.h
new file mode 100644
index 0000000000..32d0e7562c
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/extisrdrv.h
@@ -0,0 +1,41 @@
+/* extisrdrv.h
+ *
+ * This file describes the external interrupt driver
+ *
+ */
+
+#ifndef __EXT_ISR_DRIVER_H
+#define __EXT_ISR_DRIVER_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* variables */
+
+extern rtems_device_major_number rtems_externalISR_major;
+extern rtems_device_minor_number rtems_externalISR_minor;
+
+/* default external ISR driver entry */
+
+#define EXTISR_DRIVER_TABLE_ENTRY \
+ { ExternalISR_initialize, NULL, NULL, NULL, NULL, ExternalISR_control }
+
+rtems_device_driver ExternalISR_initialize(
+ rtems_device_major_number,
+ rtems_device_minor_number,
+ void *
+);
+
+rtems_device_driver ExternalISR_control(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void *pargp
+);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+/* end of include file */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/nvram.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/nvram.h
new file mode 100644
index 0000000000..246c2679c5
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/nvram.h
@@ -0,0 +1,60 @@
+/*
+ * This file contains the NvRAM driver definitions for the PPCn_60x
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#ifndef _NVRAM_H
+#define _NVRAM_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * This initializes the NvRAM driver
+ */
+
+void InitializeNvRAM(void);
+
+
+/*
+ * These routines access data in the NvRAM's OS area
+ */
+extern rtems_status_code ReadNvRAM8(unsigned32 ulOffset, unsigned8 *pucData);
+extern rtems_status_code WriteNvRAM8(unsigned32 ulOffset, unsigned8 ucValue);
+extern rtems_status_code ReadNvRAM16(unsigned32 ulOffset, unsigned16 *pusData);
+extern rtems_status_code WriteNvRAM16(unsigned32 ulOffset, unsigned16 usValue);
+extern rtems_status_code ReadNvRAM32(unsigned32 ulOffset, unsigned32 *pulData);
+extern rtems_status_code WriteNvRAM32(unsigned32 ulOffset, unsigned32 ulValue);
+rtems_status_code ReadNvRAMBlock(
+ unsigned32 ulOffset, unsigned8 *pucData, unsigned32 length);
+rtems_status_code WriteNvRAMBlock(
+ unsigned32 ulOffset, unsigned8 *ucValue, unsigned32 length);
+/*
+ * This routine returns the size of the NvRAM
+ */
+extern unsigned32 SizeNvRAM();
+
+/*
+ * This routine commits changes to the NvRAM
+ */
+extern void CommitNvRAM();
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _NVRAM_H */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/pci.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/pci.h
new file mode 100644
index 0000000000..f012d882d7
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/pci.h
@@ -0,0 +1,322 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+#ifndef _PCI_H_
+#define _PCI_H_
+
+/*
+ * PCI Configuration space definitions
+ */
+
+#define PCI_CONFIG_ADDR 0xcf8
+#define PCI_CONFIG_DATA 0xcfc
+
+#define PCI_MAX_DEVICES 16
+#define PCI_MAX_FUNCTIONS 8
+
+#define PCI_CONFIG_VENDOR_LOW 0x00
+#define PCI_CONFIG_VENDOR_HIGH 0x01
+#define PCI_CONFIG_DEVICE_LOW 0x02
+#define PCI_CONFIG_DEVICE_HIGH 0x03
+#define PCI_CONFIG_COMMAND 0x04
+#define PCI_CONFIG_STATUS 0x06
+#define PCI_CONFIG_REVISIONID 0x08
+#define PCI_CONFIG_CLASS_CODE_L 0x09
+#define PCI_CONFIG_CLASS_CODE_M 0x0a
+#define PCI_CONFIG_CLASS_CODE_U 0x0b
+#define PCI_CONFIG_CACHE_LINE_SIZE 0x0c
+#define PCI_CONFIG_LATENCY_TIMER 0x0d
+#define PCI_CONFIG_HEADER_TYPE 0x0e
+#define PCI_CONFIG_BIST 0x0f
+#define PCI_CONFIG_BAR_0 0x10
+#define PCI_CONFIG_BAR_1 0x14
+#define PCI_CONFIG_BAR_2 0x18
+#define PCI_CONFIG_BAR_3 0x1c
+#define PCI_CONFIG_BAR_4 0x20
+#define PCI_CONFIG_BAR_5 0x24
+#define PCI_CONFIG_SUBVENDOR_LOW 0x2c
+#define PCI_CONFIG_SUBVENDOR_HIGH 0x2d
+#define PCI_CONFIG_SUBDEVICE_LOW 0x2e
+#define PCI_CONFIG_SUBDEVICE_HIGH 0x2f
+#define PCI_CONFIG_ROM_BAR 0x30
+#define PCI_CONFIG_INTERRUPTLINE 0x3c
+#define PCI_CONFIG_INTERRUPTPIN 0x3d
+#define PCI_CONFIG_MIN_GNT 0x3e
+#define PCI_CONFIG_MAX_LAT 0x3f
+
+/*
+ * PCI Status register definitions
+ */
+
+#define PCI_STATUS_66MHZ_CAPABLE 0x0020
+#define PCI_STATUS_UDF_SUPPORTED 0x0040
+#define PCI_STATUS_FAST_BACK_TO_BACK 0x0080
+#define PCI_STATUS_DET_DPAR_ERR 0x0100
+#define PCI_STATUS_DEVSEL_MSK 0x0600
+#define PCI_STATUS_DEVSEL_SLOW 0x0400
+#define PCI_STATUS_DEVSEL_MED 0x0200
+#define PCI_STATUS_DEVSEL_FAST 0x0000
+#define PCI_STATUS_SIG_TARG_ABT 0x0800
+#define PCI_STATUS_REC_TARG_ABT 0x1000
+#define PCI_STATUS_REC_MAST_ABT 0x2000
+#define PCI_STATUS_SIG_SYS_ERR 0x4000
+#define PCI_STATUS_DET_PAR_ERR 0x8000
+
+/*
+ * PCI Enable register definitions
+ */
+
+#define PCI_ENABLE_IO_SPACE 0x0001
+#define PCI_ENABLE_MEMORY_SPACE 0x0002
+#define PCI_ENABLE_BUS_MASTER 0x0004
+#define PCI_ENABLE_SPECIAL_CYCLES 0x0008
+#define PCI_ENABLE_WRITE_AND_INVALIDATE 0x0010
+#define PCI_ENABLE_VGA_COMPATIBLE_PALETTE 0x0020
+#define PCI_ENABLE_PARITY 0x0040
+#define PCI_ENABLE_WAIT_CYCLE 0x0080
+#define PCI_ENABLE_SERR 0x0100
+#define PCI_ENABLE_FAST_BACK_TO_BACK 0x0200
+
+/*
+ * Bit encode for PCI_CONFIG_HEADER_TYPE register
+ */
+
+#define PCI_MULTI_FUNCTION 0x80
+
+/*
+ * Bit encodes for PCI Config BaseAddressesRegisters (BARs)
+ */
+
+#define PCI_ADDRESS_IO_SPACE 0x00000001
+#define PCI_ADDRESS_MEMORY_TYPE_MASK 0x00000007
+#define PCI_ADDRESS_MEMORY_PREFETCHABLE 0x00000008
+
+#define PCI_TYPE_32BIT 0
+#define PCI_TYPE_20BIT 2
+#define PCI_TYPE_64BIT 4
+
+/*
+ * Bit encodes for PCI Config ROMBaseAddresses
+ */
+
+#define PCI_ROMADDRESS_ENABLED 0x00000001
+
+/*
+ * PCI Bridge Configuration space definitions
+ */
+
+#define PCI_BRIDGE_PRIMARY_BUS 0x18
+#define PCI_BRIDGE_SECONDARY_BUS 0x19
+#define PCI_BRIDGE_SUBORDINATE_BUS 0x1a
+#define PCI_BRIDGE_SECONDARY_LAT 0x1b
+#define PCI_BRIDGE_IO_BASE 0x1c
+#define PCI_BRIDGE_IO_LIMIT 0x1d
+#define PCI_BRIDGE_SECONDARY_STATUS 0x1e
+#define PCI_BRIDGE_MEMORY_BASE 0x20
+#define PCI_BRIDGE_MEMORY_LIMIT 0x22
+#define PCI_BRIDGE_PRE_MEMORY_BASE 0x24
+#define PCI_BRIDGE_PRE_MEMORY_LIMIT 0x26
+#define PCI_BRIDGE_PRE_BASE_U 0x28
+#define PCI_BRIDGE_PRE_LIMIT_U 0x2c
+#define PCI_BRIDGE_IO_BASE_U 0x30
+#define PCI_BRIDGE_IO_LIMIT_U 0x32
+#define PCI_BRIDGE_ROM_BAR 0x38
+#define PCI_BRIDGE_CONTROL 0x3e
+
+/*
+ * PCI Bridge Control register definitions
+ */
+
+#define PCI_BRIDGE_PAR_ERR_RESPONSE 0x01
+#define PCI_BRIDGE_S_SERR_L_FWD_EN 0x02
+#define PCI_BRIDGE_ENABLE_ISA 0x04
+#define PCI_BRIDGE_ENABLE_VGA 0x08
+#define PCI_BRIDGE_MASTER_ABORT 0x20
+#define PCI_BRIDGE_SECONDARY_RESET 0x40
+#define PCI_BRIDGE_BACK_TO_BACK_EN 0x80
+
+/*
+ * PCI IO address forwarding capability
+ */
+#define PCI_BRIDGE_IO_CAPABILITY 0x0f
+#define PCI_BRIDGE_IO_16BIT 0x00
+#define PCI_BRIDGE_IO_32BIT 0x01
+
+/*
+ * Class codes
+ */
+#define PCI_BASE_CLASS_NULL 0x00
+#define PCI_BASE_CLASS_STORAGE 0x01
+#define PCI_BASE_CLASS_NETWORK 0x02
+#define PCI_BASE_CLASS_DISPLAY 0x03
+#define PCI_BASE_CLASS_MULTIMEDIA 0x04
+#define PCI_BASE_CLASS_MEMORY 0x05
+#define PCI_BASE_CLASS_BRIDGE 0x06
+#define PCI_BASE_CLASS_COM_CTRL 0x07
+#define PCI_BASE_CLASS_BASEPERIPH 0x08
+#define PCI_BASE_CLASS_INPUTDEV 0x09
+#define PCI_BASE_CLASS_DOCKING 0x0a
+#define PCI_BASE_CLASS_PROC 0x0b
+#define PCI_BASE_CLASS_SERBUSCTRL 0x0c
+#define PCI_BASE_CLASS_UNDEFINED 0xff
+
+#define PCI_SUB_CLASS_NULL_NVGA 0x00
+#define PCI_IF_CLASS_DISPLAY_VGA 0x00
+#define PCI_IF_CLASS_DISPLAY_VGA8514 0x01
+#define PCI_SUB_CLASS_NULL_VGA 0x01
+
+#define PCI_SUB_CLASS_STORAGE_SCSI 0x00
+#define PCI_SUB_CLASS_STORAGE_IDE 0x01
+#define PCI_SUB_CLASS_STORAGE_FLOPPY 0x02
+#define PCI_SUB_CLASS_STORAGE_IPI 0x03
+#define PCI_SUB_CLASS_STORAGE_RAID 0x04
+#define PCI_SUB_CLASS_STORAGE_OTHER 0x80
+
+#define PCI_SUB_CLASS_NETWORK_ETH 0x00
+#define PCI_SUB_CLASS_NETWORK_TOKEN 0x01
+#define PCI_SUB_CLASS_NETWORK_FDDI 0x02
+#define PCI_SUB_CLASS_NETWORK_ATM 0x03
+#define PCI_SUB_CLASS_NETWORK_OTHER 0x80
+
+#define PCI_SUB_CLASS_DISPLAY_VGA 0x00
+#define PCI_SUB_CLASS_DISPLAY_XGA 0x01
+#define PCI_SUB_CLASS_DISPLAY_OTHER 0x80
+
+#define PCI_SUB_CLASS_MULTIMEDIA_VIDEO 0x00
+#define PCI_SUB_CLASS_MULTIMEDIA_AUDIO 0x01
+#define PCI_SUB_CLASS_MULTIMEDIA_OTHER 0x80
+
+#define PCI_SUB_CLASS_MEMORY_RAM 0x00
+#define PCI_SUB_CLASS_MEMORY_FLASH 0x01
+#define PCI_SUB_CLASS_MEMORY_OTHER 0x80
+
+#define PCI_SUB_CLASS_BRIDGE_HOST 0x00
+#define PCI_SUB_CLASS_BRIDGE_ISA 0x01
+#define PCI_SUB_CLASS_BRIDGE_EISA 0x02
+#define PCI_SUB_CLASS_BRIDGE_MC 0x03
+#define PCI_SUB_CLASS_BRIDGE_PCI 0x04
+#define PCI_SUB_CLASS_BRIDGE_PCMCIA 0x05
+#define PCI_SUB_CLASS_BRIDGE_NUBUS 0x06
+#define PCI_SUB_CLASS_BRIDGE_CARDBUS 0x07
+#define PCI_SUB_CLASS_BRIDGE_OTHER 0x80
+
+#define PCI_SUB_CLASS_COM_CTRL_SERIAL 0x00
+#define PCI_IF_CLASS_COM_SER_XT 0x00
+#define PCI_IF_CLASS_COM_SER_16450 0x01
+#define PCI_IF_CLASS_COM_SER_16550 0x02
+#define PCI_SUB_CLASS_COM_CTRL_PARALLEL 0x01
+#define PCI_IF_CLASS_COM_PAR 0x00
+#define PCI_IF_CLASS_COM_PAR_BI 0x01
+#define PCI_IF_CLASS_COM_PAR_ECP 0x02
+#define PCI_SUB_CLASS_COM_CTRL_OTHER 0x80
+
+#define PCI_SUB_CLASS_BASEPERIPH_PIC 0x00
+#define PCI_IF_CLASS_BASEPERIPH_PIC 0x00
+#define PCI_IF_CLASS_BASEPERIPH_PIC_ISA 0x01
+#define PCI_IF_CLASS_BASEPERIPH_PIC_EISA 0x02
+#define PCI_SUB_CLASS_BASEPERIPH_DMA 0x01
+#define PCI_IF_CLASS_BASEPERIPH_DMA 0x00
+#define PCI_IF_CLASS_BASEPERIPH_DMA_ISA 0x01
+#define PCI_IF_CLASS_BASEPERIPH_DMA_EISA 0x02
+#define PCI_SUB_CLASS_BASEPERIPH_TIMER 0x02
+#define PCI_IF_CLASS_BASEPERIPH_TIMER 0x00
+#define PCI_IF_CLASS_BASEPERIPH_TIMER_ISA 0x01
+#define PCI_IF_CLASS_BASEPERIPH_TIMER_EISA 0x02
+#define PCI_SUB_CLASS_BASEPERIPH_RTC 0x03
+#define PCI_IF_CLASS_BASEPERIPH_RTC 0x00
+#define PCI_IF_CLASS_BASEPERIPH_RTC_ISA 0x01
+#define PCI_SUB_CLASS_BASEPERIPH_OTHER 0x80
+
+#define PCI_SUB_CLASS_INPUTDEV_KEYBOARD 0x00
+#define PCI_SUB_CLASS_INPUTDEV_PEN 0x01
+#define PCI_SUB_CLASS_INPUTDEV_MOUSE 0x02
+#define PCI_SUB_CLASS_INPUTDEV_OTHER 0x80
+
+#define PCI_SUB_CLASS_DOCKING_GENERIC 0x00
+#define PCI_SUB_CLASS_DOCKING_OTHER 0x80
+
+#define PCI_SUB_CLASS_PROC_386 0x00
+#define PCI_SUB_CLASS_PROC_486 0x01
+#define PCI_SUB_CLASS_PROC_PENTIUM 0x02
+#define PCI_SUB_CLASS_PROC_ALPHA 0x10
+#define PCI_SUB_CLASS_PROC_POWERPC 0x20
+#define PCI_SUB_CLASS_PROC_COPROC 0x40
+
+#define PCI_SUB_CLASS_SERBUSCTRL_FIREWIRE 0x00
+#define PCI_SUB_CLASS_SERBUSCTRL_ACCESS 0x01
+#define PCI_SUB_CLASS_SERBUSCTRL_SSA 0x02
+#define PCI_SUB_CLASS_SERBUSCTRL_USB 0x03
+#define PCI_SUB_CLASS_SERBUSCTRL_FIBRECHAN 0x04
+
+#define PCI_INVALID_VENDORDEVICEID 0xffffffff
+#define PCI_ID(v, d) ((d << 16) | v)
+
+/*
+ * PCI access functions
+ */
+extern rtems_status_code PCIConfigWrite8(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned8 ucValue
+);
+
+extern rtems_status_code PCIConfigWrite16(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned16 usValue
+);
+
+extern rtems_status_code PCIConfigWrite32(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned32 ulValue
+);
+
+extern rtems_status_code PCIConfigRead8(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned8 *pucValue
+);
+
+extern rtems_status_code PCIConfigRead16(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned16 *pusValue
+);
+
+extern rtems_status_code PCIConfigRead32(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned32 *pulValue
+);
+
+/*
+ * Return the number of PCI busses in the system
+ */
+extern unsigned8 BusCountPCI();
+
+#endif /* _PCI_H_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/include/tod.h b/c/src/lib/libbsp/powerpc/ppcn_60x/include/tod.h
new file mode 100644
index 0000000000..ef94d35252
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/include/tod.h
@@ -0,0 +1,38 @@
+/*
+ * Real Time Clock (MK48T08) for RTEMS on PPCn_60x
+ *
+ * Based on MVME162 TOD by:
+ * COPYRIGHT (C) 1997
+ * by Katsutoshi Shibuya - BU Denken Co.,Ltd. - Sapporo - JAPAN
+ * ALL RIGHTS RESERVED
+ *
+ * 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.
+ *
+ * $Id$
+ */
+
+
+#ifndef TOD_H
+#define TOD_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern void setRealTimeToRTEMS();
+/* Read real time from RTC and set it to RTEMS' clock manager */
+
+extern void setRealTimeFromRTEMS();
+/* Read time from RTEMS' clock manager and set it to RTC */
+
+extern int checkRealTime();
+/* Return the difference between RTC and RTEMS' clock manager time in minutes.
+ If the difference is greater than 1 day, this returns 9999. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/network/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/network/Makefile.in
new file mode 100644
index 0000000000..cef35eb353
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/network/Makefile.in
@@ -0,0 +1,54 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/network.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=amd79c970
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.c b/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.c
new file mode 100644
index 0000000000..ba3849df9a
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.c
@@ -0,0 +1,1010 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+/*
+ * RTEMS/KA9Q driver for PC-NET
+ */
+#include <bsp.h>
+#include <rtems/error.h>
+#include <ka9q/rtems_ka9q.h>
+#include <ka9q/global.h>
+#include <ka9q/enet.h>
+#include <ka9q/iface.h>
+#include <ka9q/netuser.h>
+#include <ka9q/trace.h>
+#include <ka9q/commands.h>
+
+#include <pci.h>
+#include "amd79c970.h"
+
+/*
+ * Number of PC-NETs supported by this driver
+ */
+#define NPCNETDRIVER 1
+
+/*
+ * Default number of buffer descriptors set aside for this driver.
+ * The number of transmit buffer descriptors has to be quite large
+ * since a single frame often uses four or more buffer descriptors.
+ *
+ * Set the number of Tx and Rx buffers, using Log_2(# buffers).
+ */
+#define LANCE_LOG2_TX_BUFFERS 4
+#define LANCE_LOG2_RX_BUFFERS 4
+#define TX_RING_SIZE (1 << (LANCE_LOG2_TX_BUFFERS))
+#define TX_RING_MOD_MASK (TX_RING_SIZE - 1)
+#define TX_RING_LEN_BITS ((LANCE_LOG2_TX_BUFFERS) << 4)
+#define RX_RING_SIZE (1 << (LANCE_LOG2_RX_BUFFERS))
+#define RX_RING_MOD_MASK (RX_RING_SIZE - 1)
+#define RX_RING_LEN_BITS ((LANCE_LOG2_RX_BUFFERS) << 4)
+
+/*
+ * RTEMS event used by interrupt handler to signal daemons.
+ * This must *not* be the same event used by the KA9Q task synchronization.
+ */
+#define INTERRUPT_EVENT RTEMS_EVENT_1
+
+/*
+ * Receive buffer size -- Allow for a full ethernet packet plus a pointer
+ */
+#define ETHPKT_SIZE 1520
+#define RBUF_SIZE (ETHPKT_SIZE + sizeof (struct iface *))
+
+/*
+ * LANCE Register Access Macros
+ */
+#define PCNET_IO_RD32(dp, reg, value) \
+ inport_32(&dp->pPCNet->u.dwio.##reg, value)
+#define PCNET_IO_WR32(dp, reg, value) \
+ outport_32(&dp->pPCNet->u.dwio.##reg, value)
+
+/*
+ * LANCE Register Access Macros
+ */
+#define RD_CSR32(dp, index, value) \
+ PCNET_IO_WR32(dp, rap, index); \
+ PCNET_IO_RD32(dp, rdp, value)
+
+#define WR_CSR32(dp, index, value) \
+ PCNET_IO_WR32(dp, rap, index); \
+ PCNET_IO_WR32(dp, rdp, value)
+
+#define RD_BCR32(dp, index, value) \
+ PCNET_IO_WR32(dp, rap, index); \
+ PCNET_IO_RD32(dp, bdp, value)
+
+#define WR_BCR32(dp, index, value) \
+ PCNET_IO_WR32(dp, rap, index); \
+ PCNET_IO_WR32(dp, bdp, value)
+
+/*
+ * Hardware-specific storage
+ *
+ * Note that the enetInitBlk field must be aligned to a 16 byte
+ * boundary
+ */
+typedef struct amd79c970Context {
+ rmde_t rxBdBase[RX_RING_SIZE];
+ tmde_t txBdBase[TX_RING_SIZE];
+ initblk_t initBlk;
+ pc_net_t *pPCNet;
+ unsigned32 ulIntVector;
+ struct mbuf **rxMbuf;
+ struct mbuf **txMbuf;
+ int rxBdCount;
+ int txBdCount;
+ int txBdHead;
+ int txBdTail;
+ int txBdActiveCount;
+ struct iface *iface;
+ rtems_id txWaitTid;
+
+ /*
+ * Statistics
+ */
+ unsigned long rxInterrupts;
+ unsigned long rxNotFirst;
+ unsigned long rxNotLast;
+ unsigned long rxGiant;
+ unsigned long rxNonOctet;
+ unsigned long rxRunt;
+ unsigned long rxBadCRC;
+ unsigned long rxOverrun;
+ unsigned long rxCollision;
+ unsigned long rxDiscarded;
+
+ unsigned long txInterrupts;
+ unsigned long txDeferred;
+ unsigned long txHeartbeat;
+ unsigned long txLateCollision;
+ unsigned long txRetryLimit;
+ unsigned long txUnderrun;
+ unsigned long txLostCarrier;
+ unsigned long txRawWait;
+} amd79c970Context_t;
+static amd79c970Context_t *pAmd79c970Context[NPCNETDRIVER];
+
+/*
+ * PC-NET interrupt handler
+ */
+static rtems_isr
+amd79c970_isr (rtems_vector_number v)
+{
+ unsigned32 ulCSR0, ulCSR4, ulCSR5;
+ amd79c970Context_t *dp;
+ int i;
+
+ for(i=0; i<NPCNETDRIVER; i++)
+ {
+ dp=pAmd79c970Context[i];
+ if(dp->ulIntVector==v)
+ {
+ RD_CSR32(dp, CSR0, ulCSR0);
+ if(ulCSR0 & CSR0_RINT)
+ {
+ /*
+ * We have recieve data
+ */
+ dp->rxInterrupts++;
+ rtems_event_send(
+ dp->iface->rxproc,
+ INTERRUPT_EVENT);
+ }
+
+ if(ulCSR0 & CSR0_TINT)
+ {
+ /*
+ * Data tranmitted or error
+ */
+ dp->txInterrupts++;
+ if(dp->txWaitTid)
+ {
+ rtems_event_send(
+ dp->txWaitTid,
+ INTERRUPT_EVENT);
+ }
+ }
+
+ if((ulCSR0 & CSR0_INTR) &&
+ !(ulCSR0 & (CSR0_RINT | CSR0_TINT)))
+ {
+ /*
+ * Many possible sources
+ */
+ RD_CSR32(dp, CSR4, ulCSR4);
+ RD_CSR32(dp, CSR5, ulCSR5);
+ DEBUG_puts("CSR0=");
+ DEBUG_puth(ulCSR0);
+ DEBUG_puts(", CSR4=");
+ DEBUG_puth(ulCSR4);
+ DEBUG_puts(", CSR5=");
+ DEBUG_puth(ulCSR5);
+ DEBUG_puts("\n\r");
+ /*
+ * Clear it
+ */
+ WR_CSR32(dp, CSR4, ulCSR4);
+ WR_CSR32(dp, CSR5, ulCSR5);
+ }
+
+ /*
+ * Clear interrupts
+ */
+ ulCSR0&=CSR0_BABL | CSR0_CERR | CSR0_MISS |
+ CSR0_MERR | CSR0_RINT | CSR0_TINT | CSR0_IENA;
+ WR_CSR32(dp, CSR0, ulCSR0);
+
+ RD_CSR32(dp, CSR0, ulCSR0);
+ }
+ }
+}
+
+/*
+ * Initialize the ethernet hardware
+ */
+static boolean
+amd79c970_initialize_hardware (int instance, int broadcastFlag)
+{
+ amd79c970Context_t *dp;
+ struct mbuf *bp;
+ int i;
+ unsigned8 ucPCIBusCount;
+ unsigned8 ucBusNumber;
+ unsigned8 ucSlotNumber;
+ unsigned32 ulDeviceID;
+ unsigned32 ulBAR0;
+ unsigned8 ucIntVector;
+ unsigned32 ulInitClkPCIAddr;
+ unsigned32 ulAPROM;
+ unsigned32 ulCSR0;
+
+ ucPCIBusCount=BusCountPCI();
+
+ /*
+ * Scan the available busses for instance of hardware
+ */
+ i=0;
+
+ dp=pAmd79c970Context[instance];
+ dp->pPCNet=(pc_net_t *)NULL;
+
+ for(ucBusNumber=0;
+ (ucBusNumber<ucPCIBusCount) && (dp->pPCNet==(pc_net_t *)NULL);
+ ucBusNumber++)
+ {
+ for(ucSlotNumber=0;ucSlotNumber<PCI_MAX_DEVICES;ucSlotNumber++)
+ {
+ PCIConfigRead32(ucBusNumber,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_VENDOR_LOW,
+ &ulDeviceID);
+ if(ulDeviceID!=PCI_ID(0x1022, 0x2000))
+ {
+ continue;
+ }
+
+ /*
+ * We've found a PC-NET controller
+ */
+ if(i++<instance)
+ {
+ continue;
+ }
+
+ /*
+ * Read base address
+ */
+ PCIConfigRead32(ucBusNumber,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_BAR_0,
+ &ulBAR0);
+ dp->pPCNet=(pc_net_t *)(ulBAR0&~PCI_ADDRESS_IO_SPACE);
+
+ /*
+ * Read interrupt vector
+ */
+ PCIConfigRead8(ucBusNumber,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_INTERRUPTLINE,
+ &ucIntVector);
+ dp->ulIntVector=PPCN_60X_IRQ_PCI(ucIntVector);
+
+ /*
+ * Ensure that device is enabled
+ */
+ PCIConfigWrite16(ucBusNumber,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_COMMAND,
+ PCI_ENABLE_IO_SPACE |
+ PCI_ENABLE_BUS_MASTER);
+ break;
+ }
+ }
+
+ if(dp->pPCNet==(pc_net_t *)NULL)
+ {
+ return(FALSE);
+ }
+
+ /*
+ * Read the ethernet number
+ */
+ if(!dp->iface->hwaddr)
+ {
+ dp->iface->hwaddr=mallocw (EADDR_LEN);
+ PCNET_IO_RD32(dp, aprom[0], ulAPROM);
+ for(i=0;i<4;i++)
+ {
+ dp->iface->hwaddr[i]=(ulAPROM>>(i*8))&0xff;
+ }
+ PCNET_IO_RD32(dp, aprom[1], ulAPROM);
+ for(i=0;i<2;i++)
+ {
+ dp->iface->hwaddr[i+4]=(ulAPROM>>(i*8))&0xff;
+ }
+ }
+
+ /*
+ * Allocate mbuf pointers
+ */
+ dp->rxMbuf=mallocw (dp->rxBdCount * sizeof(*dp->rxMbuf));
+ dp->txMbuf=mallocw (dp->txBdCount * sizeof(*dp->txMbuf));
+
+ /*
+ * Allocate space for incoming packets
+ */
+ for(i=0; i<dp->rxBdCount; i++)
+ {
+ dp->rxMbuf[i]=bp=ambufw (RBUF_SIZE);
+ bp->data += sizeof (struct iface *);
+ dp->rxBdBase[i].rmde_addr=
+ Swap32((unsigned32)bp->data+PCI_SYS_MEM_BASE);
+ dp->rxBdBase[i].rmde_bcnt=
+ Swap16(-(bp->size-sizeof (struct iface *)));
+ dp->rxBdBase[i].rmde_flags=Swap16(RFLG_OWN);
+ }
+
+ /*
+ * Set up transmit buffer descriptors
+ */
+ for(i=0; i<dp->txBdCount; i++)
+ {
+ dp->txBdBase[i].tmde_status=Swap16(TST_STP | TST_ENP);
+ dp->txBdBase[i].tmde_error=0;
+ dp->txMbuf[i]=NULL;
+ }
+
+ /*
+ * Initialise initblk
+ */
+ if(broadcastFlag)
+ {
+ dp->initBlk.ib_mode=0;
+ }
+ else
+ {
+ dp->initBlk.ib_mode=Swap16(CSR15_DRCVBC);
+ }
+
+ /*
+ * Set the receive descriptor ring length
+ */
+ dp->initBlk.ib_rlen=RX_RING_LEN_BITS;
+ /*
+ * Set the receive descriptor ring address
+ */
+ dp->initBlk.ib_rdra=Swap32((unsigned32)&dp->rxBdBase[0]+
+ PCI_SYS_MEM_BASE);
+
+ /*
+ * Set the transmit descriptor ring length
+ */
+ dp->initBlk.ib_tlen=TX_RING_LEN_BITS;
+ /*
+ * Set the tranmit descriptor ring address
+ */
+ dp->initBlk.ib_tdra=Swap32((unsigned32)&dp->txBdBase[0]+
+ PCI_SYS_MEM_BASE);
+
+ for(i=0;i<6;i++)
+ {
+ dp->initBlk.ib_padr[i]=dp->iface->hwaddr[i];
+ }
+
+ /*
+ * Ensure that we are in DWIO mode
+ */
+ PCNET_IO_WR32(dp, rdp, 0);
+
+ WR_CSR32(dp, 58,CSR58_PCISTYLE);
+
+ WR_CSR32(dp, CSR3,
+ CSR3_BABLM | CSR3_MERRM | CSR3_IDONM | CSR3_DXSUFLO);
+
+ WR_CSR32(dp, CSR4,
+ CSR4_APADXMIT | CSR4_MFCOM | CSR4_RCVCCOM |
+ CSR4_TXSTRTM | CSR4_JABM);
+
+ WR_CSR32(dp, CSR5, 0);
+
+ ulInitClkPCIAddr=(unsigned32)&dp->initBlk+PCI_SYS_MEM_BASE;
+ /*
+ * CSR2 must contain the high order 16 bits of the first word in
+ * the initialization block
+ */
+ WR_CSR32(dp, CSR2, (ulInitClkPCIAddr >> 16) & 0xffff);
+ /*
+ * CSR1 must contain the low order 16 bits of the first word in
+ * the initialization block
+ */
+ WR_CSR32(dp, CSR1, (ulInitClkPCIAddr & 0xffff));
+
+ /*
+ * Set up interrupts
+ */
+ set_vector(amd79c970_isr,
+ dp->ulIntVector,
+ instance);
+
+ /*
+ * Start the device
+ */
+ WR_CSR32(dp, CSR0, CSR0_INIT | CSR0_STRT);
+
+ /*
+ * Wait for 100mS for the device to initialise
+ */
+ for(i=0; i<100; i++)
+ {
+ RD_CSR32(dp, CSR0, ulCSR0);
+ if(ulCSR0 & CSR0_IDON)
+ {
+ break;
+ }
+ rtems_ka9q_ppause(1); /* 1mS */
+ }
+ if(i >= 100)
+ {
+ return(FALSE);
+ }
+
+ /*
+ * Enable interrupts
+ */
+ WR_CSR32(dp, CSR0, CSR0_IENA);
+
+ dp->txBdHead=dp->txBdTail=0;
+ dp->txBdActiveCount=0;
+
+ return(TRUE);
+}
+
+/*
+ * Soak up buffer descriptors that have been sent
+ */
+static void
+amd79c970_retire_tx_bd (amd79c970Context_t *dp)
+{
+ unsigned16 status;
+ unsigned32 error;
+ int i;
+ int nRetired;
+
+ i = dp->txBdTail;
+ nRetired = 0;
+ while((dp->txBdActiveCount != 0) &&
+ (((status=Swap16(dp->txBdBase[i].tmde_status)) & TST_OWN)==0))
+ {
+ /*
+ * See if anything went wrong
+ */
+ if(status & TST_ERR)
+ {
+ /*
+ * Check for errors
+ */
+ error=Swap16(dp->txBdBase[i].tmde_error);
+
+ if (error & TERR_LCOL)
+ dp->txLateCollision++;
+ if (error & TERR_RTRY)
+ dp->txRetryLimit++;
+ if (error & TERR_UFLO)
+ dp->txUnderrun++;
+ if (error & TERR_EXDEF)
+ dp->txDeferred++;
+ if (error & TERR_LCAR)
+ dp->txLostCarrier++;
+ }
+ nRetired++;
+ if (status & TST_ENP)
+ {
+ /*
+ * A full frame has been transmitted.
+ * Free all the associated buffer descriptors.
+ */
+ dp->txBdActiveCount -= nRetired;
+ while (nRetired) {
+ nRetired--;
+ free_mbuf (&dp->txMbuf[dp->txBdTail]);
+ if (++dp->txBdTail == dp->txBdCount)
+ dp->txBdTail = 0;
+ }
+ }
+ if (++i == dp->txBdCount)
+ {
+ i = 0;
+ }
+ }
+}
+
+/*
+ * Send raw packet (caller provides header).
+ * This code runs in the context of the interface transmit
+ * task or in the context of the network task.
+ */
+static int
+amd79c970_raw (struct iface *iface, struct mbuf **bpp)
+{
+ amd79c970Context_t *dp;
+ struct mbuf *bp;
+ tmde_t *firstTxBd, *txBd;
+ unsigned16 status;
+ int nAdded;
+
+ dp = pAmd79c970Context[iface->dev];
+
+ /*
+ * Fill in some logging data
+ */
+ iface->rawsndcnt++;
+ iface->lastsent = secclock ();
+ dump (iface, IF_TRACE_OUT, *bpp);
+
+ /*
+ * It would not do to have two tasks active in the transmit
+ * loop at the same time.
+ * The blocking is simple-minded since the odds of two tasks
+ * simultaneously attempting to use this code are low. The only
+ * way that two tasks can try to run here is:
+ * 1) Task A enters this code and ends up having to
+ * wait for a transmit buffer descriptor.
+ * 2) Task B gains control and tries to transmit a packet.
+ * The RTEMS/KA9Q scheduling semaphore ensures that there
+ * are no race conditions associated with manipulating the
+ * txWaitTid variable.
+ */
+ if (dp->txWaitTid) {
+ dp->txRawWait++;
+ while (dp->txWaitTid)
+ rtems_ka9q_ppause (10);
+ }
+
+ /*
+ * Free up buffer descriptors
+ */
+ amd79c970_retire_tx_bd (dp);
+
+ /*
+ * Set up the transmit buffer descriptors.
+ * No need to pad out short packets since the
+ * hardware takes care of that automatically.
+ * No need to copy the packet to a contiguous buffer
+ * since the hardware is capable of scatter/gather DMA.
+ */
+ bp = *bpp;
+ nAdded = 0;
+ txBd = firstTxBd = dp->txBdBase + dp->txBdHead;
+ for (;;) {
+ /*
+ * Wait for buffer descriptor to become available.
+ */
+ if ((dp->txBdActiveCount + nAdded) == dp->txBdCount) {
+ /*
+ * Find out who we are
+ */
+ if (dp->txWaitTid == 0)
+ rtems_task_ident (0, 0, &dp->txWaitTid);
+
+ /*
+ * Wait for buffer descriptor to become available.
+ * Note that the buffer descriptors are checked
+ * *before* * entering the wait loop -- this catches
+ * the possibility that a buffer descriptor became
+ * available between the `if' above, and the clearing
+ * of the event register.
+ * Also, the event receive doesn't wait forever.
+ * This is to catch the case where the transmitter
+ * stops in the middle of a frame -- and only the
+ * last buffer descriptor in a frame can generate
+ * an interrupt.
+ */
+ amd79c970_retire_tx_bd (dp);
+ while ((dp->txBdActiveCount + nAdded) == dp->txBdCount) {
+ rtems_ka9q_event_receive (INTERRUPT_EVENT,
+ RTEMS_WAIT|RTEMS_EVENT_ANY,
+ 1 + 1000000/BSP_Configuration.microseconds_per_tick);
+ amd79c970_retire_tx_bd (dp);
+ }
+ }
+
+ /*
+ * Fill in the buffer descriptor
+ */
+ txBd->tmde_addr=Swap32((unsigned32)bp->data+PCI_SYS_MEM_BASE);
+ txBd->tmde_bcnt=Swap16(-bp->cnt);
+ dp->txMbuf[dp->txBdHead] = bp;
+
+ nAdded++;
+ if (++dp->txBdHead == dp->txBdCount)
+ {
+ dp->txBdHead = 0;
+ }
+
+ /*
+ * Set the transmit buffer status.
+ * Break out of the loop if this mbuf is the last in the frame.
+ */
+ if ((bp = bp->next) == NULL) {
+ if(txBd==firstTxBd)
+ {
+ /*
+ * There is only one frame
+ */
+ txBd->tmde_status=Swap16(TST_OWN |
+ TST_STP |
+ TST_ENP);
+ }
+ else
+ {
+ /*
+ * Mark the last buffer
+ */
+ txBd->tmde_status=Swap16(TST_OWN |
+ TST_ENP);
+ /*
+ * Trigger the first transmit
+ */
+ firstTxBd->tmde_status=Swap16(TST_OWN |
+ TST_STP);
+ }
+ /*
+ * Sync instruction required to overcome the Grackle
+ * stale data bug
+ */
+ asm volatile("sync");
+ dp->txBdActiveCount += nAdded;
+ break;
+ }
+ else if(txBd!=firstTxBd)
+ {
+ txBd->tmde_status = Swap16(TST_OWN);
+ }
+ txBd = dp->txBdBase + dp->txBdHead;
+ }
+
+ /*
+ * Show that we've finished with the packet
+ */
+ dp->txWaitTid = 0;
+ *bpp = NULL;
+ return 0;
+}
+
+/*
+ * PC-NET reader task
+ */
+static void
+amd79c970_rx (int dev, void *p1, void *p2)
+{
+ struct iface *iface=(struct iface *)p1;
+ amd79c970Context_t *dp=(amd79c970Context_t *)p2;
+ struct mbuf *bp;
+ rtems_unsigned16 status;
+ rmde_t *rxBd;
+ int rxBdIndex;
+ int continuousCount;
+
+ /*
+ * Input packet handling loop
+ */
+ continuousCount=0;
+ rxBdIndex=0;
+
+ while(TRUE)
+ {
+ rxBd=&dp->rxBdBase[rxBdIndex];
+
+ /*
+ * Wait for packet if there's not one ready
+ */
+ if((status=Swap16(rxBd->rmde_flags)) & RFLG_OWN)
+ {
+ /*
+ * Reset `continuous-packet' count
+ */
+ continuousCount=0;
+
+ /*
+ * Wait for packet
+ * Note that the buffer descriptor is checked
+ * *before* the event wait -- this catches the
+ * possibility that a packet arrived between the
+ * `if' above, and the clearing of the event register.
+ */
+ while ((status=Swap16(rxBd->rmde_flags)) & RFLG_OWN)
+ {
+ rtems_ka9q_event_receive (INTERRUPT_EVENT,
+ RTEMS_WAIT|RTEMS_EVENT_ANY,
+ RTEMS_NO_TIMEOUT);
+ }
+ }
+
+ /*
+ * Check that packet is valid
+ */
+ if((status & RFLG_ERR) ||
+ ((status & (RFLG_STP|RFLG_ENP)) != (RFLG_STP|RFLG_ENP)))
+ {
+ /*
+ * Something went wrong with the reception
+ */
+ if(!(status & RFLG_ENP))
+ dp->rxNotLast++;
+ if(!(status & RFLG_STP))
+ dp->rxNotFirst++;
+ if(status & RFLG_OFLO)
+ dp->rxGiant++;
+ if(status & RFLG_FRAM)
+ dp->rxNonOctet++;
+ if(status & RFLG_CRC)
+ dp->rxBadCRC++;
+ if(status & RFLG_BUFF)
+ dp->rxOverrun++;
+ }
+ else
+ {
+ /*
+ * Pass the packet up the chain
+ * The mbuf count is reduced to remove
+ * the frame check sequence at the end
+ * of the packet.
+ */
+ bp=dp->rxMbuf[rxBdIndex];
+ bp->cnt=Swap16(rxBd->rmde_mcnt) - sizeof (uint32);
+ net_route (iface, &bp);
+
+ /*
+ * Give the network code a chance to digest the
+ * packet. This guards against a flurry of
+ * incoming packets (usually an ARP storm) from
+ * using up all the available memory.
+ */
+ if(++continuousCount >= dp->rxBdCount)
+ kwait_null ();
+
+ /*
+ * Allocate a new mbuf
+ * FIXME: It seems to me that it would be better
+ * if there were some way to limit number of mbufs
+ * in use by this interface, but I don't see any
+ * way of determining when the mbuf we pass up
+ * is freed.
+ */
+ dp->rxMbuf[rxBdIndex]=bp=ambufw (RBUF_SIZE);
+ bp->data += sizeof (struct iface *);
+ rxBd->rmde_addr=Swap32(
+ (unsigned32)bp->data+PCI_SYS_MEM_BASE);
+ rxBd->rmde_bcnt=Swap16(
+ -(bp->size-sizeof (struct iface *)));
+ }
+
+ /*
+ * Reenable the buffer descriptor
+ */
+ rxBd->rmde_flags=Swap16(RFLG_OWN);
+
+ /*
+ * Move to next buffer descriptor
+ */
+ if(++rxBdIndex==dp->rxBdCount)
+ rxBdIndex=0;
+ }
+}
+
+/*
+ * Shut down the interface
+ * FIXME: This is a pretty simple-minded routine. It doesn't worry
+ * about cleaning up mbufs, shutting down daemons, etc.
+ */
+static int
+amd79c970_stop (struct iface *iface)
+{
+ amd79c970Context_t *dp;
+ unsigned32 ulCSR0;
+ int i;
+
+ dp=pAmd79c970Context[iface->dev];
+
+ /*
+ * Stop the device
+ */
+ WR_CSR32(dp, CSR0, CSR0_STOP);
+
+ /*
+ * Wait for 100mS for the device to stop
+ */
+ for(i=0; i<100; i++)
+ {
+ RD_CSR32(dp, CSR0, ulCSR0);
+ if(!(ulCSR0 & (CSR0_RXON | CSR0_TXON)))
+ {
+ break;
+ }
+ rtems_ka9q_ppause(1); /* 1mS */
+ }
+ if(i >= 100)
+ {
+ return(-1);
+ }
+
+ /*
+ * Free up all the mbufs we've allocated
+ */
+ for(i=0; i<dp->rxBdCount; i++)
+ {
+ free_mbuf(&dp->rxMbuf[i]);
+ }
+
+ return 0;
+}
+
+/*
+ * Show interface statistics
+ */
+static void
+amd79c970_show (struct iface *iface)
+{
+ int i;
+
+ i=iface->dev;
+
+ printf (" Rx Interrupts:%-8lu", pAmd79c970Context[i]->rxInterrupts);
+ printf (" Not First:%-8lu", pAmd79c970Context[i]->rxNotFirst);
+ printf (" Not Last:%-8lu\n", pAmd79c970Context[i]->rxNotLast);
+ printf (" Giant:%-8lu", pAmd79c970Context[i]->rxGiant);
+ printf (" Runt:%-8lu", pAmd79c970Context[i]->rxRunt);
+ printf (" Non-octet:%-8lu\n", pAmd79c970Context[i]->rxNonOctet);
+ printf (" Bad CRC:%-8lu", pAmd79c970Context[i]->rxBadCRC);
+ printf (" Overrun:%-8lu", pAmd79c970Context[i]->rxOverrun);
+ printf (" Collision:%-8lu\n", pAmd79c970Context[i]->rxCollision);
+ printf (" Discarded:%-8lu\n", pAmd79c970Context[i]->rxDiscarded);
+
+ printf (" Tx Interrupts:%-8lu", pAmd79c970Context[i]->txInterrupts);
+ printf (" Deferred:%-8lu", pAmd79c970Context[i]->txDeferred);
+ printf (" Missed Hearbeat:%-8lu\n", pAmd79c970Context[i]->txHeartbeat);
+ printf (" No Carrier:%-8lu", pAmd79c970Context[i]->txLostCarrier);
+ printf ("Retransmit Limit:%-8lu", pAmd79c970Context[i]->txRetryLimit);
+ printf (" Late Collision:%-8lu\n", pAmd79c970Context[i]->txLateCollision);
+ printf (" Underrun:%-8lu", pAmd79c970Context[i]->txUnderrun);
+ printf (" Raw output wait:%-8lu\n", pAmd79c970Context[i]->txRawWait);
+}
+
+/*
+ * Attach an PC-NET driver to the system
+ * This is the only `extern' function in the driver.
+ *
+ * argv[0]: interface label, e.g., "amd79c970"
+ * argv[1]: maximum transmission unit, bytes, e.g., "1500"
+ * argv[2]: accept ("broadcast") or ignore ("nobroadcast") broadcast packets
+ * Following arguments are optional, but if present, must appear in
+ * the following order:
+ * Following arguments are optional, but if Ethernet address is
+ * specified, Internet address must also be specified.
+ * ###.###.###.### -- IP address
+ * ##:##:##:##:##:## -- Ethernet address
+ */
+int
+rtems_ka9q_driver_attach (int argc, char *argv[], void *p)
+{
+ struct iface *iface;
+ struct amd79c970Context *dp;
+ char *cp;
+ int i;
+ int argIndex;
+ int broadcastFlag;
+
+ /*
+ * Find a free driver
+ */
+ for(i=0; i<NPCNETDRIVER; i++)
+ {
+ if(pAmd79c970Context[i]==NULL)
+ break;
+ }
+ if(i==NPCNETDRIVER)
+ {
+ printf ("Too many PC-NET drivers.\n");
+ return -1;
+ }
+ if(if_lookup (argv[0]) != NULL)
+ {
+ printf ("Interface %s already exists\n", argv[0]);
+ return -1;
+ }
+
+ /*
+ * Note that this structure must be aligned to a 16 byte boundary
+ */
+ pAmd79c970Context[i]=(amd79c970Context_t *)
+ (((unsigned32)callocw(1,
+ sizeof(amd79c970Context_t)+16)+16) & ~15);
+ dp=pAmd79c970Context[i];
+
+ /*
+ * Create an interface descriptor
+ */
+ iface=callocw (1, sizeof *iface);
+ iface->name=strdup (argv[0]);
+ iface->mtu=atoi (argv[1]);
+
+ /*
+ * Select broadcast packet handling
+ */
+ cp=argv[2];
+ if(strnicmp (cp, "broadcast", strlen (cp))==0)
+ {
+ broadcastFlag=1;
+ }
+ else if(strnicmp (cp, "nobroadcast", strlen (cp))==0)
+ {
+ broadcastFlag=0;
+ }
+ else {
+ printf ("Argument `%s' is neither `broadcast' nor `nobroadcast'.\n", cp);
+ return -1;
+ }
+ argIndex=3;
+
+ /*
+ * Set receive buffer descriptor count
+ */
+ dp->rxBdCount=RX_RING_SIZE;
+
+ /*
+ * Set transmit buffer descriptor count
+ */
+ dp->txWaitTid=0;
+ dp->txBdCount=TX_RING_SIZE;
+
+ /*
+ * Set Internet address
+ */
+ if(argIndex<argc)
+ iface->addr=resolve (argv[argIndex++]);
+ else
+ iface->addr=Ip_addr;
+
+ /*
+ * Set Ethernet address
+ */
+ if(argIndex<argc)
+ {
+ iface->hwaddr=mallocw (EADDR_LEN);
+ gether (iface->hwaddr, argv[argIndex++]);
+ }
+
+ iface->dev=i;
+ iface->raw=amd79c970_raw;
+ iface->stop=amd79c970_stop;
+ iface->show=amd79c970_show;
+ dp->iface=iface;
+ setencap (iface, "Ethernet");
+
+ /*
+ * Set up PC-NET hardware
+ */
+ if(!amd79c970_initialize_hardware (i, broadcastFlag))
+ {
+ printf ("Unable to initialize hardware for %s\n", argv[0]);
+ return -1;
+ }
+
+ /*
+ * Chain onto list of interfaces
+ */
+ iface->next=Ifaces;
+ Ifaces=iface;
+
+ /*
+ * Start I/O daemons
+ */
+ cp=if_name (iface, " tx");
+ iface->txproc=newproc (cp, 1024, if_tx, iface->dev, iface, NULL, 0);
+ free (cp);
+ cp=if_name (iface, " rx");
+ iface->rxproc=newproc (cp, 1024, amd79c970_rx, iface->dev, iface, dp, 0);
+ free (cp);
+ return 0;
+}
+
+/*
+ * FIXME: There should be an ioctl routine to allow things like
+ * enabling/disabling reception of broadcast packets.
+ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.h b/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.h
new file mode 100644
index 0000000000..dd30d90b0d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/network/amd79c970.h
@@ -0,0 +1,426 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+#ifndef _PCNET_H
+#define _PCNET_H
+
+/*
+ * IO space structure for the AMD79C970 device
+ */
+
+typedef volatile struct pc_net
+{
+ union
+ {
+ struct {
+ unsigned16 aprom[8]; /* 0x00 */
+ unsigned16 rdp; /* 0x10 */
+ unsigned16 rap; /* 0x14 */
+ unsigned16 reset; /* 0x18 */
+ unsigned16 bdp; /* 0x1C */
+ } wio;
+ struct {
+ unsigned32 aprom[4]; /* 0x00 */
+ unsigned32 rdp; /* 0x10 */
+ unsigned32 rap; /* 0x12 */
+ unsigned32 reset; /* 0x14 */
+ unsigned32 bdp; /* 0x16 */
+ } dwio;
+ } u;
+} pc_net_t;
+
+/*
+ * The EEPROM is 2Kbit (128bytes)
+ */
+#define EEPROM_SIZE 128
+#define EEPROM_HEAD_SIZE 36
+
+typedef struct pc_net_eeprom {
+ unsigned8 EthNumber[6];
+ unsigned16 Reserved1; /* Must be 0x0000 */
+ unsigned16 Reserved2; /* Must be 0x1000 */
+ unsigned16 User1;
+ unsigned16 checksum;
+ unsigned16 Reserved3; /* Must be 0x5757 */
+ unsigned16 bcr16;
+ unsigned16 bcr17;
+ unsigned16 bcr18;
+ unsigned16 bcr2;
+ unsigned16 bcr21;
+ unsigned16 Reserved4; /* Must be 0x0000 */
+ unsigned16 Reserved5; /* Must be 0x0000 */
+ unsigned8 Reserved6; /* Must be 0x00 */
+ unsigned8 checksumAdjust;
+ unsigned16 Reserved7; /* Must be 0x0000 */
+ unsigned16 crc; /* CCITT checksum from Serial[] onwards */
+ unsigned8 Serial[16]; /* Radstone Serial Number */
+} pc_net_eeprom_t;
+
+/*
+ * PCnet-PCI Single Chip Ethernet Controller for PCI Local Bus
+ */
+/*
+ * Register and bit definitions
+ */
+
+#define CSR0 0
+#define CSR1 1
+#define CSR2 2
+#define CSR3 3
+#define CSR4 4
+#define CSR5 5
+#define CSR6 6
+#define CSR7 7
+#define CSR8 8
+#define CSR9 9
+#define CSR15 15
+#define CSR47 47
+#define CSR82 82 /* Bus Activity Timer */
+#define CSR100 100 /* Memory Error Timeout register */
+#define CSR114 114
+#define CSR122 122 /* Receiver Packet Alignment Register */
+
+#define BCR2 2 /* Misc. Configuration */
+#define BCR18 18 /* Bus size and burst control */
+#define DEFAULT_BCR18 0x2162 /* default BCR18 value - was 0x21e2*/
+#define BCR19 19
+#define BCR20 20 /* Software Style */
+#define BCR21 21
+
+#define APROM0 0x00
+#define APROM1 0x04
+#define APROM2 0x08
+
+/*
+ * CSR0: Bit definitions
+ */
+#define CSR0_ERR 0x8000 /* error summary */
+#define CSR0_BABL 0x4000 /* babble error */
+#define CSR0_CERR 0x2000 /* collision error */
+#define CSR0_MISS 0x1000 /* missed packet */
+#define CSR0_MERR 0x0800 /* memory error */
+#define CSR0_RINT 0x0400 /* receiver interrupt */
+#define CSR0_TINT 0x0200 /* transmitter interrupt */
+#define CSR0_IDON 0x0100 /* initialization done */
+#define CSR0_INTR 0x0080 /* interrupt flag */
+#define CSR0_IENA 0x0040 /* interrupt enable */
+#define CSR0_RXON 0x0020 /* receiver on */
+#define CSR0_TXON 0x0010 /* transmitter on */
+#define CSR0_TDMD 0x0008 /* transmit demand */
+#define CSR0_STOP 0x0004 /* stop the ilacc */
+#define CSR0_STRT 0x0002 /* start the ilacc */
+#define CSR0_INIT 0x0001 /* initialize the ilacc */
+
+#define CSR3_BABLM 0x4000 /* BABL Mask */
+#define CSR3_MISSM 0x1000 /* Missed packet Mask */
+#define CSR3_MERRM 0x0800 /* Memory error Mask */
+#define CSR3_RINTM 0x0400 /* Receive Interrupt Mask */
+#define CSR3_TINTM 0x0200 /* Transmit Interrupt Mask */
+#define CSR3_IDONM 0x0100 /* Initialization Done Mask */
+#define CSR3_DXSUFLO 0x0040 /* Disable tx stop on underrun */
+#define CSR3_LAPPEN 0x0020 /* lookahead packet proc enable */
+#define CSR3_DXMT2PD 0x0010 /* disable 2 part deferral */
+#define CSR3_EMBA 0x0008 /* enable modified backoff */
+#define CSR3_BSWP 0x0004 /* byte swap */
+
+#define CSR4_DMAPLUS 0x4000 /* DMA burst transfer until FIFO empty */
+#define CSR4_BACON_68K 0x0040 /* 32 bit 680x0 */
+#define CSR4_TXSTRT 0x0008 /* Transmit STaRT status */
+#define CSR4_TXSTRTM 0x0004 /* Transmit STaRT interrupt Mask */
+#define CSR4_ENTST 0x8000 /* enable test mode */
+#define CSR4_TIMER 0x2000 /* enable bus timer csr82 */
+#define CSR4_DPOLL 0x1000 /* disable tx polling */
+#define CSR4_APADXMIT 0x0800 /* auto pad tx to 64 */
+#define CSR4_ASTRPRCV 0x0400 /* auto strip rx pad and fcs */
+#define CSR4_MFCO 0x0200 /* missed frame counter oflo interrupt */
+#define CSR4_MFCOM 0x0100 /* mask to disable */
+#define CSR4_RCVCCO 0x0020 /* rx collision counter oflo interrupt */
+#define CSR4_RCVCCOM 0x0010 /* mask to disable */
+#define CSR4_JAB 0x0002 /* jabber error 10baseT interrupt */
+#define CSR4_JABM 0x0001 /* mask to disable */
+
+#define CSR5_SPND 0x0001 /* Suspend */
+
+#define CSR15_PROM 0x8000 /* Promiscuous */
+#define CSR15_DRCVBC 0x4000 /* Disable receiver broadcast */
+#define CSR15_DRCVPA 0x2000 /* Disable receiver phys. addr. */
+#define CSR15_DLNKTST 0x1000 /* Disable link status */
+#define CSR15_DAPC 0x0800 /* Disable auto polarity det. */
+#define CSR15_MENDECL 0x0400 /* MENDEC loopback mode */
+#define CSR15_LRT 0x0200 /* Low receiver threshold */
+#define CSR15_TSEL 0x0200 /* Transmit mode select */
+#define CSR15_INTL 0x0040 /* Internal loopback */
+#define CSR15_DRTY 0x0020 /* Disable retry */
+#define CSR15_FCOLL 0x0010 /* Force collision */
+#define CSR15_DXMTFCS 0x0008 /* Disable transmit CRC */
+#define CSR15_LOOP 0x0004 /* Loopback enable */
+#define CSR15_DTX 0x0002 /* Disable transmitter */
+#define CSR15_DRX 0x0001 /* Disable receiver */
+
+#define CSR58_PCISTYLE 0x0002 /* software style */
+
+#define CSR80_RCVFW16 (0<<12) /* fifo level to trigger rx dma */
+#define CSR80_RCVFW32 (1<<12)
+#define CSR80_RCVFW64 (2<<12)
+#define CSR80_XMTSP4 (0<<10) /* fifo level to trigger tx */
+#define CSR80_XMTSP16 (1<<10)
+#define CSR80_XMTSP64 (2<<10)
+#define CSR80_XMTSP112 (3<<10)
+#define CSR80_XMTFW16 (0<<8) /* fifo level to stop dma */
+#define CSR80_XMTFW32 (1<<8)
+#define CSR80_XMTFW64 (2<<8)
+/* must also clear csr4 CSR4_DMAPLUS: */
+#define CSR80_DMATC(x) ((x)&0xff) /* max transfers per burst. deflt 16 */
+/*
+ * must also set csr4 CSR4_TIMER:
+ */
+#define CSR82_DMABAT(x) ((x)&0xffff) /* max burst time nanosecs*100 */
+
+#define BCR18_MUSTSET 0x0100 /* this bit must be written as 1 !! */
+#define BCR18_BREADE 0x0040 /* linear burst enable. yes ! on pci */
+#define BCR18_BWRITE 0x0020 /* in write direction */
+#define BCR18_LINBC4 0x0001 /* linear burst count 4 8 or 16 */
+#define BCR18_LINBC8 0x0002 /* NOTE LINBC must be <= fifo trigger*/
+#define BCR18_LINBC16 0x0004
+
+#define BCR19_PVALID 0x8000 /* aprom (eeprom) read checksum ok */
+
+/*
+ * initial setting of csr0
+ */
+#define CSR0_IVALUE (CSR0_IDON | CSR0_IENA | CSR0_STRT | CSR0_INIT)
+
+/*
+ * our setting of csr3
+ */
+#define CSR3_VALUE (CSR3_ACON | CSR3_BSWP)
+
+/*
+ * Initialization Block.
+ * Chip initialization includes the reading of the init block to obtain
+ * the operating parameters.
+ *
+ * This essentially consists of 7, 32 bit LE words. In the following the
+ * fields are ordered so that they map correctly in BE mode, however each
+ * 16 and 32 byte field will require swapping.
+ */
+
+typedef volatile struct initblk {
+ /* mode can be set in csr15 */
+ unsigned16 ib_mode; /* Chip's operating parameters */
+ unsigned8 ib_rlen; /* rx ring length (power of 2) */
+ unsigned8 ib_tlen; /* tx ring length (power of 2) */
+/*
+ * The bytes must be swapped within the word, so that, for example,
+ * the address 8:0:20:1:25:5a is written in the order
+ * 0 8 1 20 5a 25
+ * For PCI970 that is long word swapped: so no swapping needed, since
+ * the bus will swap.
+ */
+ unsigned8 ib_padr[8]; /* physical address */
+ unsigned16 ib_ladrf[4]; /* logical address filter */
+ unsigned32 ib_rdra; /* rcv ring desc addr */
+ unsigned32 ib_tdra; /* xmit ring desc addr */
+} initblk_t;
+
+
+/*
+ * bits in mode register: allows alteration of the chips operating parameters
+ */
+#define IBM_PROM 0x8000 /* promiscuous mode */
+/*
+ * mode is also in cr15
+ */
+#define MODE_DRCVBC 0x4000 /* disable receive broadcast */
+#define MODE_DRCVPA 0x2000 /* disable receive physical address */
+#define MODE_DLNKTST 0x1000 /* disable link status monitoring 10T */
+#define MODE_DAPC 0x0800 /* disable auto polarity 10T */
+#define MODE_MENDECL 0x0400 /* mendec loopback */
+#define MODE_LRT 0x0200 /* low receive threshold/tx mode sel tmau */
+#define MODE_PORTSEL10T 0x0080 /* port select 10T ?? */
+#define MODE_PORTSELAUI 0x0000 /* port select aui ?? */
+#define IBM_INTL 0x0040 /* internal loopback */
+#define IBM_DRTY 0x0020 /* disable retry */
+#define IBM_COLL 0x0010 /* force collision */
+#define IBM_DTCR 0x0008 /* disable transmit crc */
+#define IBM_LOOP 0x0004 /* loopback */
+#define IBM_DTX 0x0002 /* disable transmitter */
+#define IBM_DRX 0x0001 /* disable receiver */
+
+/*
+ * Buffer Management is accomplished through message descriptors organized
+ * in ring structures in main memory. There are two rings allocated for the
+ * device: a receive ring and a transmit ring. The following defines the
+ * structure of the descriptor rings.
+ */
+
+/*
+ * Receive List type definition
+ *
+ * This essentially consists of 4, 32 bit LE words. In the following the
+ * fields are ordered so that they map correctly in BE mode, however each
+ * 16 and 32 byte field will require swapping.
+ */
+
+typedef volatile struct rmde {
+ unsigned32 rmde_addr; /* buf addr */
+
+ unsigned16 rmde_bcnt;
+ unsigned16 rmde_flags;
+
+ unsigned16 rmde_mcnt;
+ unsigned16 rmde_misc;
+
+ unsigned32 align;
+} rmde_t;
+
+
+/*
+ * bits in the flags field
+ */
+#define RFLG_OWN 0x8000 /* ownership bit, 1==LANCE */
+#define RFLG_ERR 0x4000 /* error summary */
+#define RFLG_FRAM 0x2000 /* framing error */
+#define RFLG_OFLO 0x1000 /* overflow error */
+#define RFLG_CRC 0x0800 /* crc error */
+#define RFLG_BUFF 0x0400 /* buffer error */
+#define RFLG_STP 0x0200 /* start of packet */
+#define RFLG_ENP 0x0100 /* end of packet */
+
+/*
+ * bits in the buffer byte count field
+ */
+#define RBCNT_ONES 0xf000 /* must be ones */
+#define RBCNT_BCNT 0x0fff /* buf byte count, in 2's compl */
+
+/*
+ * bits in the message byte count field
+ */
+#define RMCNT_RES 0xf000 /* reserved, read as zeros */
+#define RMCNT_BCNT 0x0fff /* message byte count */
+
+/*
+ * Transmit List type definition
+ *
+ * This essentially consists of 4, 32 bit LE words. In the following the
+ * fields are ordered so that they map correctly in BE mode, however each
+ * 16 and 32 byte field will require swapping.
+ */
+typedef volatile struct tmde {
+ unsigned32 tmde_addr; /* buf addr */
+
+ unsigned16 tmde_bcnt;
+ unsigned16 tmde_status; /* misc error and status bits */
+
+ unsigned32 tmde_error;
+
+ unsigned32 align;
+} tmde_t;
+
+/*
+ * bits in the status field
+ */
+#define TST_OWN 0x8000 /* ownership bit, 1==LANCE */
+#define TST_ERR 0x4000 /* error summary */
+#define TST_RES 0x2000 /* reserved bit */
+#define TST_MORE 0x1000 /* more than one retry was needed */
+#define TST_ONE 0x0800 /* one retry was needed */
+#define TST_DEF 0x0400 /* defer while trying to transmit */
+#define TST_STP 0x0200 /* start of packet */
+#define TST_ENP 0x0100 /* end of packet */
+
+/*
+ * setting of status field when packet is to be transmitted
+ */
+#define TST_XMIT (TST_STP | TST_ENP | TST_OWN)
+
+/*
+ * bits in the buffer byte count field
+ */
+#define TBCNT_ONES 0xf000 /* must be ones */
+#define TBCNT_BCNT 0x0fff /* buf byte count, in 2's compl */
+
+/*
+ * bits in the error field
+ */
+#define TERR_BUFF 0x8000 /* buffer error */
+#define TERR_UFLO 0x4000 /* underflow error */
+#define TERR_EXDEF 0x2000 /* excessive deferral */
+#define TERR_LCOL 0x1000 /* late collision */
+#define TERR_LCAR 0x0800 /* loss of carrier */
+#define TERR_RTRY 0x0400 /* retry error */
+#define TERR_TDR 0x03ff /* time domain reflectometry */
+
+/*
+ * Defines pertaining to statistics gathering (diagnostic only)
+ */
+
+/*
+ * receive errors
+ */
+#define ERR_FRAM 0 /* framing error */
+#define ERR_OFLO 1 /* overflow error */
+#define ERR_CRC 2 /* crc error */
+#define ERR_RBUFF 3 /* receive buffer error */
+
+/*
+ * transmit errors
+ */
+#define ERR_MORE 4 /* more than one retry */
+#define ERR_ONE 5 /* one retry */
+#define ERR_DEF 6 /* defer'd packet */
+#define ERR_TBUFF 7 /* transmit buffer error */
+#define ERR_UFLO 8 /* underflow error */
+#define ERR_LCOL 9 /* late collision */
+#define ERR_LCAR 10 /* loss of carrier */
+#define ERR_RTRY 11 /* retry error, >16 retries */
+
+/*
+ * errors reported in csr0
+ */
+#define ERR_BABL 12 /* transmitter timeout error */
+#define ERR_MISS 13 /* missed packet */
+#define ERR_MEM 14 /* memory error */
+#define ERR_CERR 15 /* collision errors */
+#define XMIT_INT 16 /* transmit interrupts */
+#define RCV_INT 17 /* receive interrupts */
+
+#define NHARD_ERRORS 18 /* error types used in diagnostic */
+
+/*
+ * other statistics
+ */
+#define ERR_TTOUT 18 /* transmit timeouts */
+#define ERR_ITOUT 19 /* init timeouts */
+#define ERR_INITS 20 /* reinitializations */
+#define ERR_RSILO 21 /* silo ptrs misaligned on recv */
+#define ERR_TSILO 22 /* silo ptrs misaligned on xmit */
+#define ERR_SINTR 23 /* spurious interrupts */
+
+#define NUM_ERRORS 24 /* number of errors types */
+
+/*
+ * Bit definitions for BCR19
+ */
+#define prom_EDI (unsigned16)0x0001
+#define prom_EDO (unsigned16)0x0001
+#define prom_ESK (unsigned16)0x0002
+#define prom_ECS (unsigned16)0x0004
+#define prom_EEN (unsigned16)0x0010
+#define prom_EEDET (unsigned16)0x2000
+#define prom_PVALID (unsigned16)0x8000
+#define prom_PREAD (unsigned16)0x4000
+
+#endif
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/Makefile.in
new file mode 100644
index 0000000000..5cf4e06e0e
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/Makefile.in
@@ -0,0 +1,56 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/nvram.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=$(NVRAM_PIECES)
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+NVRAM_PIECES=nvram
+
+#
+# (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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/ds1385.h b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/ds1385.h
new file mode 100644
index 0000000000..c4861d9c80
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/ds1385.h
@@ -0,0 +1,39 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+/*
+ * Definitions for the ds1385 NvRAM
+ */
+
+#ifndef _DS1385_H
+#define _DS1385_H
+
+#include "prepnvr.h"
+
+#define DS1385_NVSIZE 4096 /* size of NVRAM */
+#define DS1385_GESIZE (DS1385_NVSIZE-CONFSIZE-OSAREASIZE-sizeof(HEADER))
+#define DS1385_PORT_BASE 0x74
+
+/* Here is the whole map of the DS1385 NVRAM */
+typedef struct _DS1385_NVRAM_MAP {
+ HEADER Header;
+ unsigned char GEArea[DS1385_GESIZE];
+ unsigned char OSArea[OSAREASIZE];
+ unsigned char ConfigArea[CONFSIZE];
+ } DS1385_NVRAM_MAP, *PDS1385_NVRAM_MAP;
+
+#endif /* _DS1385_H */
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/mk48t18.h b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/mk48t18.h
new file mode 100644
index 0000000000..f4aa3be106
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/mk48t18.h
@@ -0,0 +1,87 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+/*
+ * Definitions for the mk48t18 RTC/NvRAM
+ */
+
+#ifndef _MK48T18_H
+#define _MK48T18_H
+
+#include "prepnvr.h"
+
+/*
+ * This structure maps to the top of the NvRAM. It is based on the standard
+ * CMOS.h file for the ds1385. Feature and system dependant areas are preserved
+ * for potential compatibility issues.
+ *
+ * The CRC's are computed with x**16+x**12+x**5 + 1 polynomial
+ * The clock is kept in 24 hour BCD mode and should be set to UT(GMT)
+ */
+
+typedef struct _MK48T18_CMOS_MAP {
+ unsigned8 SystemDependentArea2[8];
+ unsigned8 FeatureByte0[1];
+ unsigned8 FeatureByte1[1];
+ unsigned8 Century; /* century byte in BCD */
+ unsigned8 FeatureByte3[1];
+ unsigned8 FeatureByte4[1];
+ unsigned8 FeatureByte5[1];
+ unsigned8 FeatureByte6[1];
+ unsigned8 FeatureByte7[1];
+ unsigned8 BootPW[14];
+ rtems_unsigned16 BootCrc; /* CRC on BootPW */
+ unsigned8 ConfigPW[14];
+ rtems_unsigned16 ConfigCrc; /* CRC on ConfigPW */
+ unsigned8 SystemDependentArea1[8];
+ /*
+ * The following are the RTC registers
+ */
+ volatile unsigned8 Control;
+ volatile unsigned8 Second:7; /* 0-59 */
+ volatile unsigned8 Stop:1;
+ volatile unsigned8 Minute; /* 0-59 */
+ volatile unsigned8 Hour; /* 0-23 */
+ volatile unsigned8 Day:3; /* 1-7 */
+ volatile unsigned8 Resvd1:3; /* 0 */
+ volatile unsigned8 FT:1; /* Frequency test bit - must be 0 */
+ volatile unsigned8 Resvd2:1; /* 0 */
+ volatile unsigned8 Date; /* 1-31 */
+ volatile unsigned8 Month; /* 1-12 */
+ volatile unsigned8 Year; /* 0-99 */
+} MK48T18_CMOS_MAP, *PMK48T18_CMOS_MAP;
+
+/*
+ * Control register definitions
+ */
+#define MK48T18_CTRL_WRITE 0x80
+#define MK48T18_CTRL_READ 0x40
+#define MK48T18_CTRL_SIGN 0x20
+
+#define MK48T18_NVSIZE 8192-sizeof(MK48T18_CMOS_MAP)
+#define MK48T18_GESIZE (MK48T18_NVSIZE-CONFSIZE-OSAREASIZE-sizeof(HEADER))
+#define MK48T18_BASE (PMK48T18_NVRAM_MAP)((unsigned8 *)PCI_MEM_BASE+0x00800000)
+
+/* Here is the whole map of the MK48T18 NVRAM */
+typedef struct _MK48T18_NVRAM_MAP {
+ HEADER Header;
+ unsigned8 GEArea[MK48T18_GESIZE];
+ unsigned8 OSArea[OSAREASIZE];
+ unsigned8 ConfigArea[CONFSIZE];
+ MK48T18_CMOS_MAP CMOS;
+} MK48T18_NVRAM_MAP, *PMK48T18_NVRAM_MAP;
+
+#endif /* _MK48T18_H */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/nvram.c b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/nvram.c
new file mode 100644
index 0000000000..bf085c968b
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/nvram.c
@@ -0,0 +1,515 @@
+/*
+ * This file contains the NvRAM driver for the PPCn_60x
+ *
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#include <bsp.h>
+#include "ds1385.h"
+#include "mk48t18.h"
+#include "stk11c68.h"
+
+/*
+ * Private types
+ */
+typedef
+void
+(*PNVRAMWRITE)
+(
+ unsigned32 ulOffset,
+ unsigned8 ucByte
+);
+
+typedef
+unsigned8
+(*PNVRAMREAD)
+(
+ unsigned32 ulOffset
+);
+
+typedef
+void
+(*PNVRAMCOMMIT)
+(
+);
+
+typedef struct _NVRAM_ENTRY_TABLE
+{
+ PNVRAMWRITE nvramWrite;
+ PNVRAMREAD nvramRead;
+ PNVRAMCOMMIT nvramCommit;
+ unsigned32 nvramSize;
+} NVRAM_ENTRY_TABLE, *PNVRAM_ENTRY_TABLE;
+
+/*
+ * Private routines
+ */
+
+/*
+ * This routine provides a stub for NvRAM devices which
+ * do not require a commit operation
+ */
+static void nvramCommitStub();
+
+/*
+ * DS1385 specific routines
+ */
+static void nvramDsWrite(unsigned32 ulOffset, unsigned8 ucByte);
+static unsigned8 nvramDsRead(unsigned32 ulOffset);
+
+/*
+ * MK48T18 specific routines
+ */
+static void nvramMkWrite(unsigned32 ulOffset, unsigned8 ucByte);
+static unsigned8 nvramMkRead(unsigned32 ulOffset);
+
+/*
+ * STK11C68 specific routines
+ */
+static void nvramStk11C68Commit();
+/*
+ * STK11C88 specific routines
+ */
+static void nvramStk11C88Commit();
+
+/*
+ * NvRAM hook tables
+ */
+NVRAM_ENTRY_TABLE nvramDsTable =
+{
+ nvramDsWrite,
+ nvramDsRead,
+ nvramCommitStub,
+ DS1385_NVSIZE
+};
+
+NVRAM_ENTRY_TABLE nvramMkTable =
+{
+ nvramMkWrite,
+ nvramMkRead,
+ nvramCommitStub,
+ MK48T18_NVSIZE
+};
+
+/*
+ * As the STK devicxe is at the same address as the MK device,
+ * the MK read/write routines may be used
+ */
+NVRAM_ENTRY_TABLE nvramStkTable =
+{
+ nvramMkWrite,
+ nvramMkRead,
+ nvramStk11C68Commit,
+ STK11C68_NVSIZE
+};
+
+NVRAM_ENTRY_TABLE nvramStk88Table =
+{
+ nvramMkWrite,
+ nvramMkRead,
+ nvramStk11C88Commit,
+ STK11C88_NVSIZE
+};
+
+/*
+ * Private variables
+ */
+static PNVRAM_ENTRY_TABLE pNvRAMFunc;
+static boolean bNvRAMChanged=FALSE;
+static unsigned32 ulPRePOSAreaLength;
+static unsigned32 ulPRePOSAreaOffset;
+
+/*
+ * Mutual-exclusion semaphore
+ */
+static rtems_id semNvRAM;
+
+/*
+ * These routines support the ds1385
+ */
+static unsigned8 nvramDsRead(unsigned32 ulOffset)
+{
+ unsigned8 ucTemp;
+
+ ucTemp = ulOffset & 0xff;
+ outport_byte(DS1385_PORT_BASE, ucTemp);
+
+ ucTemp = (ulOffset >> 8) & 0xf;
+ outport_byte((DS1385_PORT_BASE + 1) , ucTemp);
+
+ inport_byte(DS1385_PORT_BASE+3, ucTemp);
+ return(ucTemp);
+}
+
+static void nvramDsWrite(unsigned32 ulOffset, unsigned8 ucData)
+{
+ unsigned8 ucTemp;
+
+ ucTemp = (unsigned8)(ulOffset & 0xff);
+ outport_byte(DS1385_PORT_BASE, (unsigned8) ucTemp);
+
+ ucTemp = (unsigned8)((ulOffset >> 8) & 0xf);
+ outport_byte((DS1385_PORT_BASE + 1) , (unsigned8)ucTemp);
+
+ outport_byte((DS1385_PORT_BASE+3), ucData);
+}
+
+/*
+ * These routines support the MK48T18 and STK11C68
+ */
+static unsigned8 nvramMkRead(unsigned32 ulOffset)
+{
+ unsigned8 *pNvRAM = (unsigned8 *)MK48T18_BASE;
+
+ return(pNvRAM[ulOffset]);
+}
+
+static void nvramMkWrite(unsigned32 ulOffset, unsigned8 ucData)
+{
+ unsigned8 *pNvRAM = (unsigned8 *)MK48T18_BASE;
+
+ pNvRAM[ulOffset]=ucData;
+}
+
+/*
+ * This routine provides a stub for NvRAM devices which
+ * do not require a commit operation
+ */
+static void nvramCommitStub()
+{
+}
+
+/*
+ * This routine triggers a transfer from the NvRAM to the
+ * EE array in the STK11C68 device
+ */
+static void nvramStk11C68Commit()
+{
+#if 0
+ rtems_interval ticks_per_second;
+ rtems_status_code status;
+#endif
+
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ /*
+ * Issue Store command
+ */
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x0000);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x1555);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x0aaa);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x1fff);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x10f0);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x0f0f);
+ EIEIO;
+ /*
+ * Delay for 10mS to allow store to
+ * complete
+ */
+#if 0
+ status = rtems_clock_get(
+ RTEMS_CLOCK_GET_TICKS_PER_SECOND,
+ &ticks_per_second
+ );
+
+ status = rtems_task_wake_after(ticks_per_second/100);
+#endif
+ bNvRAMChanged=FALSE;
+
+ rtems_semaphore_release(semNvRAM);
+}
+
+/*
+ * This routine triggers a transfer from the NvRAM to the
+ * EE array in the STK11C88 device
+ */
+static void nvramStk11C88Commit()
+{
+#if 0
+ rtems_interval ticks_per_second;
+ rtems_status_code status;
+#endif
+
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ /*
+ * Issue Store command
+ */
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x0e38);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x31c7);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x03e0);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x3c1f);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x303f);
+ EIEIO;
+ (void)pNvRAMFunc->nvramRead(0x0fc0);
+ EIEIO;
+ /*
+ * Delay for 10mS to allow store to
+ * complete
+ */
+#if 0
+ status = rtems_clock_get(
+ RTEMS_CLOCK_GET_TICKS_PER_SECOND,
+ &ticks_per_second
+ );
+
+ status = rtems_task_wake_after(ticks_per_second/100);
+#endif
+ bNvRAMChanged=FALSE;
+
+ rtems_semaphore_release(semNvRAM);
+}
+
+/*
+ * These are the publically accessable routines
+ */
+/*
+ * This routine returns the size of the NvRAM
+ */
+unsigned32 SizeNvRAM()
+{
+ return(ulPRePOSAreaLength);
+}
+
+/*
+ * This routine commits changes to the NvRAM
+ */
+void CommitNvRAM()
+{
+ if(bNvRAMChanged)
+ {
+ (pNvRAMFunc->nvramCommit)();
+ }
+}
+
+/*
+ * This routine reads a byte from the NvRAM
+ */
+rtems_status_code ReadNvRAM8(unsigned32 ulOffset, unsigned8 *pucData)
+{
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ *pucData=pNvRAMFunc->nvramRead(ulPRePOSAreaOffset+ulOffset);
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * This routine writes a byte to the NvRAM
+ */
+rtems_status_code WriteNvRAM8(unsigned32 ulOffset, unsigned8 ucValue)
+{
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ pNvRAMFunc->nvramWrite(ulPRePOSAreaOffset+ulOffset, ucValue);
+ bNvRAMChanged=TRUE;
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * This routine reads a block of bytes from the NvRAM
+ */
+rtems_status_code ReadNvRAMBlock(
+ unsigned32 ulOffset, unsigned8 *pucData, unsigned32 length)
+{
+ unsigned32 i;
+
+ if((ulOffset + length) > ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ for ( i=0 ; i<length ; i++ )
+ pucData[i] =
+ pNvRAMFunc->nvramRead(ulPRePOSAreaOffset+ulOffset+i);
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * This routine writes a block of bytes to the NvRAM
+ */
+rtems_status_code WriteNvRAMBlock(
+ unsigned32 ulOffset, unsigned8 *ucValue, unsigned32 length)
+{
+ unsigned32 i;
+
+ if((ulOffset + length) > ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+
+ for ( i=0 ; i<length ; i++ )
+ pNvRAMFunc->nvramWrite(
+ ulPRePOSAreaOffset+ulOffset+i, ucValue[i]);
+ bNvRAMChanged=TRUE;
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * The NVRAM holds data in Big-Endian format
+ */
+rtems_status_code ReadNvRAM16 (unsigned32 ulOffset, unsigned16 *pusData)
+{
+ unsigned32 ulTrueOffset=ulPRePOSAreaOffset+ulOffset;
+
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ *pusData=(pNvRAMFunc->nvramRead(ulTrueOffset) << 8) +
+ (pNvRAMFunc->nvramRead(ulTrueOffset + 1));
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code WriteNvRAM16 (unsigned32 ulOffset, unsigned16 usValue)
+{
+ unsigned32 ulTrueOffset=ulPRePOSAreaOffset+ulOffset;
+
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ pNvRAMFunc->nvramWrite(ulTrueOffset, (unsigned8) (usValue >> 8));
+ pNvRAMFunc->nvramWrite(ulTrueOffset + 1, (unsigned8) usValue);
+ bNvRAMChanged=TRUE;
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code ReadNvRAM32 (unsigned32 ulOffset, unsigned32 *pulData)
+{
+ unsigned32 ulTrueOffset=ulPRePOSAreaOffset+ulOffset;
+
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ *pulData=(pNvRAMFunc->nvramRead(ulTrueOffset) << 24) +
+ (pNvRAMFunc->nvramRead(ulTrueOffset + 1) << 16) +
+ (pNvRAMFunc->nvramRead(ulTrueOffset + 2) << 8) +
+ (pNvRAMFunc->nvramRead(ulTrueOffset + 3));
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code WriteNvRAM32 (unsigned32 ulOffset, unsigned32 ulValue)
+{
+ unsigned32 ulTrueOffset=ulPRePOSAreaOffset+ulOffset;
+
+ if(ulOffset>ulPRePOSAreaLength)
+ {
+ return RTEMS_INVALID_ADDRESS;
+ }
+ rtems_semaphore_obtain(semNvRAM, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ pNvRAMFunc->nvramWrite(ulTrueOffset, (unsigned8) (ulValue >> 24));
+ pNvRAMFunc->nvramWrite(ulTrueOffset + 1, (unsigned8) (ulValue >> 16));
+ pNvRAMFunc->nvramWrite(ulTrueOffset + 2, (unsigned8) (ulValue >> 8));
+ pNvRAMFunc->nvramWrite(ulTrueOffset + 3, (unsigned8) ulValue);
+ bNvRAMChanged=TRUE;
+ rtems_semaphore_release(semNvRAM);
+ return(RTEMS_SUCCESSFUL);
+}
+
+void
+InitializeNvRAM(void)
+{
+ PHEADER pNvHeader = (PHEADER)0;
+ rtems_status_code sc;
+ unsigned32 ulLength, ulOffset;
+
+ if(ucSystemType==SYS_TYPE_PPC1)
+ {
+ if(ucBoardRevMaj<5)
+ {
+ pNvRAMFunc=&nvramDsTable;
+ }
+ else
+ {
+ pNvRAMFunc=&nvramMkTable;
+ }
+ }
+ else if(ucSystemType==SYS_TYPE_PPC1a)
+ {
+ pNvRAMFunc=&nvramMkTable;
+ }
+ else if(ucSystemType==SYS_TYPE_PPC4)
+ {
+ pNvRAMFunc=&nvramStk88Table;
+ }
+ else
+ {
+ pNvRAMFunc=&nvramStkTable;
+ }
+
+ /*
+ * Set up mutex semaphore
+ */
+ sc = rtems_semaphore_create (
+ rtems_build_name ('N', 'V', 'R', 's'),
+ 1,
+ RTEMS_BINARY_SEMAPHORE |
+ RTEMS_INHERIT_PRIORITY |
+ RTEMS_PRIORITY,
+ RTEMS_NO_PRIORITY,
+ &semNvRAM);
+ if (sc != RTEMS_SUCCESSFUL)
+ {
+ rtems_fatal_error_occurred (sc);
+ }
+
+ /*
+ * Initially access the whole of NvRAM until we determine where the
+ * OS Area is located.
+ */
+ ulPRePOSAreaLength=0xffffffff;
+ ulPRePOSAreaOffset=0;
+
+ /*
+ * Access the header at the start of NvRAM
+ */
+ ReadNvRAM32((unsigned32)(&pNvHeader->OSAreaLength), &ulLength);
+ ReadNvRAM32((unsigned32)(&pNvHeader->OSAreaAddress), &ulOffset);
+
+ /*
+ * Now set limits for future accesses
+ */
+ ulPRePOSAreaLength=ulLength;
+ ulPRePOSAreaOffset=ulOffset;
+}
+
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/prepnvr.h b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/prepnvr.h
new file mode 100644
index 0000000000..cf55a4525d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/prepnvr.h
@@ -0,0 +1,127 @@
+/* Structure map for NVRAM on PowerPC Reference Platform */
+
+/* Revision 1 changes (8/25/94):
+ - Power Management (RESTART_BLOCK struct)
+ - Normal added to PM_MODE
+ - OSIRQMask (HEADER struct) */
+
+/* All fields are either character/byte strings which are valid either
+endian or they are big-endian numbers.
+
+There are a number of Date and Time fields which are in RTC format,
+big-endian. These are stored in UT (GMT).
+
+For enum's: if given in hex then they are bit significant, i.e. only
+one bit is on for each enum.
+*/
+
+#ifndef _NVRAM_
+#define _NVRAM_
+
+#define VERSION 1
+#define REVISION 0
+
+#define OSAREASIZE 1024 /* size of OSArea space */
+#define CONFSIZE 512 /* guess at size of Configuration space */
+
+typedef struct _SECURITY {
+ unsigned long BootErrCnt; /* Count of boot password errors */
+ unsigned long ConfigErrCnt; /* Count of config password errors */
+ unsigned long BootErrorDT[2]; /* Date&Time from RTC of last error in pw */
+ unsigned long ConfigErrorDT[2]; /* Date&Time from RTC of last error in pw */
+ unsigned long BootCorrectDT[2]; /* Date&Time from RTC of last correct pw */
+ unsigned long ConfigCorrectDT[2]; /* Date&Time from RTC of last correct pw */
+ unsigned long BootSetDT[2]; /* Date&Time from RTC of last set of pw */
+ unsigned long ConfigSetDT[2]; /* Date&Time from RTC of last set of pw */
+ unsigned char Serial[16]; /* Box serial number */
+ } SECURITY;
+
+typedef enum _OS_ID {
+ Unknown = 0,
+ Firmware = 1,
+ AIX = 2,
+ NT = 3,
+ WPOS2 = 4,
+ WPAIX = 5,
+ Taligent = 6,
+ Solaris = 7,
+ Netware = 8,
+ USL = 9,
+ Low_End_Client = 10,
+ SCO = 11
+ } OS_ID;
+
+typedef struct _ERROR_LOG {
+ unsigned char ErrorLogEntry[40]; /* To be architected */
+ } ERROR_LOG;
+
+/*---Revision 1: Change the following struct:---*/
+typedef struct _RESUME_BLOCK {
+ /* Hibernation Resume Device will be an
+ environment variable */
+ unsigned long CheckSum; /* Checksum of RESUME_BLOCK */
+ volatile unsigned long BootStatus;
+
+ void * ResumeAddr; /* For Suspend Resume */
+ void * SaveAreaAddr; /* For Suspend Resume */
+ unsigned long SaveAreaLength; /* For Suspend Resume */
+
+ unsigned long HibResumeImageRBA; /* RBA (512B blocks) of compressed OS
+ memory image to be loaded by FW
+ on Resume from hibernation */
+ unsigned long HibResumeImageRBACount; /* Size of image in 512B blocks*/
+ unsigned long Reserved;
+ } RESUME_BLOCK;
+
+typedef enum _OSAREA_USAGE {
+ Empty = 0,
+ Used = 1
+ } OSAREA_USAGE;
+
+typedef enum _PM_MODE {
+ Suspend = 0x80, /* Part of state is in memory */
+ Hibernate = 0x40, /* Nothing in memory - state saved elsewhere */
+/* Revision 1: Normal added (actually was already here) */
+ Normal = 0x00 /* No power management in effect */
+ } PMMode;
+
+typedef struct _HEADER {
+ unsigned short Size; /* NVRAM size in K(1024) */
+ unsigned char Version; /* Structure map different */
+ unsigned char Revision; /* Structure map the same -
+ may be new values in old fields
+ in other words old code still works */
+ unsigned short Crc1; /* check sum from beginning of nvram to OSArea */
+ unsigned short Crc2; /* check sum of config */
+ unsigned char LastOS; /* OS_ID */
+ unsigned char Endian; /* B if big endian, L if little endian */
+ unsigned char OSAreaUsage; /* OSAREA_USAGE */
+ unsigned char PMMode; /* Shutdown mode */
+ RESUME_BLOCK ResumeBlock;
+ SECURITY Security;
+ ERROR_LOG ErrorLog[2];
+
+/* Global Environment information */
+ void * GEAddress;
+ unsigned long GELength;
+ /* Date&Time from RTC of last change to Global Environment */
+ unsigned long GELastWriteDT[2];
+
+/* Configuration information */
+ void * ConfigAddress;
+ unsigned long ConfigLength;
+ /* Date&Time from RTC of last change to Configuration */
+ unsigned long ConfigLastWriteDT[2];
+ unsigned long ConfigCount; /* Count of entries in Configuration */
+
+/* OS dependent temp area */
+ void * OSAreaAddress;
+ unsigned long OSAreaLength;
+ /* Date&Time from RTC of last change to OSAreaArea */
+ unsigned long OSAreaLastWriteDT[2];
+
+/* Revision 1: add this mask - function tbd */
+ /*unsigned short OSIRQMask; OS to FW IRQ Mask - "I've used this one" */
+ } HEADER, *PHEADER;
+
+ #endif /* ndef _NVRAM_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/stk11c68.h b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/stk11c68.h
new file mode 100644
index 0000000000..118662905b
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/nvram/stk11c68.h
@@ -0,0 +1,46 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+/*
+ * Definitions for the stk11C68 NvRAM
+ */
+
+#ifndef _STK11C68_H
+#define _STK11C68_H
+
+#include "prepnvr.h"
+
+/*
+ * STK11C68 definitions
+ */
+#define STK11C68_NVSIZE 8192
+#define STK11C68_GESIZE (STK11C68_NVSIZE-CONFSIZE-OSAREASIZE-sizeof(HEADER))
+#define STK11C68_BASE (PSTK11C68_NVRAM_MAP)((unsigned8 *)PCI_MEM_BASE+0x00800000)
+
+/*
+ * STK11C88 definitions
+ */
+#define STK11C88_NVSIZE 0x8000-sizeof(MK48T18_CMOS_MAP)
+
+/* Here is the whole map of the STK11C68 NVRAM */
+typedef struct _STK11C68_NVRAM_MAP {
+ HEADER Header;
+ unsigned8 GEArea[STK11C68_GESIZE];
+ unsigned8 OSArea[OSAREASIZE];
+ unsigned8 ConfigArea[CONFSIZE];
+} STK11C68_NVRAM_MAP, *PSTK11C68_NVRAM_MAP;
+
+#endif /* _STK11C68_H */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/pci/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/pci/Makefile.in
new file mode 100644
index 0000000000..941fc1ada7
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/pci/Makefile.in
@@ -0,0 +1,56 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/pci.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=$(PCI_PIECES)
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+PCI_PIECES=pci
+
+#
+# (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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/pci/pci.c b/c/src/lib/libbsp/powerpc/ppcn_60x/pci/pci.c
new file mode 100644
index 0000000000..909a568d55
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/pci/pci.c
@@ -0,0 +1,342 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+#include <bsp.h>
+#include <pci.h>
+
+/* SCE 97/4/9
+ *
+ * Use PCI configuration space access mechanism 1
+ *
+ * This is the preferred access mechanism and must be used when accessing
+ * bridged PCI busses.
+ *
+ * The address to be written to the PCI_CONFIG_ADDRESS port is constructed
+ * thus (the representation below is little endian):
+ *
+ * 31 30 24 23 16 15 11 10 8 7 2 1 0
+ * ----------------------------------------------------------------------
+ * | 1 | Resvd | Bus Number | Dev Number | Fn Number | Reg Number | 0 | 0 |
+ * ----------------------------------------------------------------------
+ *
+ * On bus 0, the first 'real' device is at Device number 11, the Eagle being
+ * device 0. On all other busses, device numbering starts at 0.
+ */
+/*
+ * Normal PCI device numbering on busses other than 0 is such that
+ * that the first device (0) is attached to AD16, second (1) to AD17 etc.
+ */
+#define CONFIG_ADDRESS(Bus, Device, Function, Offset) \
+ (0x80000000 | (Bus<<16) | \
+ ((Device+(((Bus==0)&&(Device>0)) ? 10 : 0))<<11) | \
+ (Function<<8) | \
+ (Offset&~0x03))
+#define BYTE_LANE_OFFSET(Offset) ((Offset)&0x3)
+
+/*
+ * Private data
+ */
+static unsigned8 ucMaxPCIBus;
+
+/*
+ * Public routines
+ */
+rtems_status_code PCIConfigWrite8(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned8 ucValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Write to the configuration space data register with the appropriate
+ * offset
+ */
+ outport_byte(PCI_CONFIG_DATA+BYTE_LANE_OFFSET(ucOffset), ucValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code PCIConfigWrite16(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned16 usValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Write to the configuration space data register with the appropriate
+ * offset
+ */
+ outport_16(PCI_CONFIG_DATA+BYTE_LANE_OFFSET(ucOffset), usValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code PCIConfigWrite32(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned32 ulValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Write to the configuration space data register with the appropriate
+ * offset
+ */
+ outport_32(PCI_CONFIG_DATA, ulValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code PCIConfigRead8(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned8 *pucValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Read from the configuration space data register with the appropriate
+ * offset
+ */
+ inport_byte(PCI_CONFIG_DATA+BYTE_LANE_OFFSET(ucOffset), *pucValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code PCIConfigRead16(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned16 *pusValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Read from the configuration space data register with the appropriate
+ * offset
+ */
+ inport_16(PCI_CONFIG_DATA+BYTE_LANE_OFFSET(ucOffset), *pusValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+rtems_status_code PCIConfigRead32(
+ unsigned8 ucBusNumber,
+ unsigned8 ucSlotNumber,
+ unsigned8 ucFunctionNumber,
+ unsigned8 ucOffset,
+ unsigned32 *pulValue
+)
+{
+ ISR_Level Irql;
+
+ /*
+ * Ensure that accesses to the addr/data ports are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ /*
+ * Write to the configuration space address register
+ */
+ outport_32(PCI_CONFIG_ADDR,
+ CONFIG_ADDRESS(ucBusNumber, ucSlotNumber,
+ ucFunctionNumber, ucOffset));
+ /*
+ * Read from the configuration space data register with the appropriate
+ * offset
+ */
+ inport_32(PCI_CONFIG_DATA, *pulValue);
+
+ _ISR_Enable(Irql);
+
+ return(RTEMS_SUCCESSFUL);
+}
+
+/*
+ * This routine determines the maximum bus number in the system
+ */
+void InitializePCI()
+{
+ unsigned8 ucSlotNumber, ucFnNumber, ucNumFuncs;
+ unsigned8 ucHeader;
+ unsigned8 ucBaseClass, ucSubClass, ucMaxSubordinate;
+ unsigned32 ulDeviceID;
+
+ /*
+ * Scan PCI bus 0 looking for PCI-PCI bridges
+ */
+ for(ucSlotNumber=0;ucSlotNumber<PCI_MAX_DEVICES;ucSlotNumber++)
+ {
+ (void)PCIConfigRead32(0,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_VENDOR_LOW,
+ &ulDeviceID);
+ if(ulDeviceID==PCI_INVALID_VENDORDEVICEID)
+ {
+ /*
+ * This slot is empty
+ */
+ continue;
+ }
+ (void)PCIConfigRead8(0,
+ ucSlotNumber,
+ 0,
+ PCI_CONFIG_HEADER_TYPE,
+ &ucHeader);
+ if(ucHeader&PCI_MULTI_FUNCTION)
+ {
+ ucNumFuncs=PCI_MAX_FUNCTIONS;
+ }
+ else
+ {
+ ucNumFuncs=1;
+ }
+ for(ucFnNumber=0;ucFnNumber<ucNumFuncs;ucFnNumber++)
+ {
+ (void)PCIConfigRead32(0,
+ ucSlotNumber,
+ ucFnNumber,
+ PCI_CONFIG_VENDOR_LOW,
+ &ulDeviceID);
+ if(ulDeviceID==PCI_INVALID_VENDORDEVICEID)
+ {
+ /*
+ * This slot/function is empty
+ */
+ continue;
+ }
+
+ /*
+ * This slot/function has a device fitted.
+ */
+ (void)PCIConfigRead8(0,
+ ucSlotNumber,
+ ucFnNumber,
+ PCI_CONFIG_CLASS_CODE_U,
+ &ucBaseClass);
+ (void)PCIConfigRead8(0,
+ ucSlotNumber,
+ ucFnNumber,
+ PCI_CONFIG_CLASS_CODE_M,
+ &ucSubClass);
+ if((ucBaseClass==PCI_BASE_CLASS_BRIDGE) &&
+ (ucSubClass==PCI_SUB_CLASS_BRIDGE_PCI))
+ {
+ /*
+ * We have found a PCI-PCI bridge
+ */
+ (void)PCIConfigRead8(0,
+ ucSlotNumber,
+ ucFnNumber,
+ PCI_BRIDGE_SUBORDINATE_BUS,
+ &ucMaxSubordinate);
+ if(ucMaxSubordinate>ucMaxPCIBus)
+ {
+ ucMaxPCIBus=ucMaxSubordinate;
+ }
+ }
+ }
+ }
+}
+
+/*
+ * Return the number of PCI busses in the system
+ */
+unsigned8 BusCountPCI()
+{
+ return(ucMaxPCIBus+1);
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/start/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/start/Makefile.in
new file mode 100644
index 0000000000..3e7884433a
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/start/Makefile.in
@@ -0,0 +1,54 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${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) $(CC_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+CLOBBER_ADDITIONS +=
+
+all: ${ARCH} $(SRCS) $(OBJS) $(PGM)
+ $(INSTALL_VARIANT) -m 555 ${PGM} ${PROJECT_RELEASE}/lib
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/start/start.S b/c/src/lib/libbsp/powerpc/ppcn_60x/start/start.S
new file mode 100644
index 0000000000..a8dc4cb3b0
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/start/start.S
@@ -0,0 +1,153 @@
+/*
+ * This is based on the mvme-crt0.S file from libgloss/rs6000.
+ * crt0.S -- startup file for PowerPC systems.
+ *
+ * (c) 1998, Radstone Technology plc.
+ *
+ *
+ * This is an unpublished work the copyright in which vests
+ * in Radstone Technology plc. All rights reserved.
+ *
+ * The information contained herein is the property of Radstone
+ * Technology plc. and is supplied without liability for
+ * errors or omissions and no part may be reproduced, used or
+ * disclosed except as authorized by contract or other written
+ * permission. The copyright and the foregoing
+ * restriction on reproduction, use and disclosure extend to
+ * all the media in which this information may be
+ * embodied.
+ *
+ * Copyright (c) 1995 Cygnus Support
+ *
+ * The authors hereby grant permission to use, copy, modify, distribute,
+ * and license this software and its documentation for any purpose, provided
+ * that existing copyright notices are retained in all copies and that this
+ * notice is included verbatim in any distributions. No written agreement,
+ * license, or royalty fee is required for any of the authorized uses.
+ * Modifications to this software may be copyrighted by their authors
+ * and need not follow the licensing terms described here, provided that
+ * the new terms are clearly indicated on the first page of each file where
+ * they apply.
+ *
+ * $Id$
+ */
+#include <rtems/score/targopts.h>
+#include "ppc-asm.h"
+#include "bsp.h"
+
+ .file "start.s"
+
+ .extern FUNC_NAME(atexit)
+ .globl FUNC_NAME(__atexit)
+ .section ".sdata","aw"
+ .align 2
+FUNC_NAME(__atexit): /* tell C's eabi-ctor's we have an atexit function */
+ .long FUNC_NAME(atexit)@fixup /* and that it is to register __do_global_dtors */
+
+ .section ".fixup","aw"
+ .align 2
+ .long FUNC_NAME(__atexit)
+
+ .text
+ .globl _start
+ .type _start,@function
+_start:
+ /* Set MSR */
+ /*
+ * Enable data and instruction address translation and floating point
+ */
+ li r3,MSR_IR | MSR_DR | MSR_FP
+ mtmsr r3
+
+ /*
+ * The caches are already flushed by the firmware so just enable
+ */
+ mfspr r3,HID0
+#if PPC_USE_DATA_CACHE
+ /*
+ * Enable data and instruction cache
+ */
+ ori r3,r3 ,H0_60X_ICE | H0_60X_DCE
+#else
+ /*
+ * Enable instruction cache only
+ */
+ ori r3,r3 ,H0_60X_ICE
+#endif
+ mtspr HID0,r3
+
+ /* clear bss */
+ lis r6,__bss_start@h
+ ori r6,r6,__bss_start@l
+ lis r7,__bss_end@h
+ ori r7,r7,__bss_end@l
+
+ cmplw 1,r6,r7
+ bc 4,4,.Lbss_done
+
+ subf r8,r6,r7 /* number of bytes to zero */
+ srwi r9,r8,2 /* number of words to zero */
+ mtctr r9
+ li r0,0 /* zero to clear memory */
+ addi r6,r6,-4 /* adjust so we can use stwu */
+.Lbss_loop:
+ stwu r0,4(r6) /* zero bss */
+ bdnz .Lbss_loop
+
+.Lbss_done:
+
+ /* clear sbss */
+ lis r6,__sbss_start@h
+ ori r6,r6,__sbss_start@l
+ lis r7,__sbss_end@h
+ ori r7,r7,__sbss_end@l
+
+ cmplw 1,r6,r7
+ bc 4,4,.Lsbss_done
+
+ subf r8,r6,r7 /* number of bytes to zero */
+ srwi r9,r8,2 /* number of words to zero */
+ mtctr r9
+ li r0,0 /* zero to clear memory */
+ addi r6,r6,-4 /* adjust so we can use stwu */
+.Lsbss_loop:
+ stwu r0,4(r6) /* zero sbss */
+ bdnz .Lsbss_loop
+
+.Lsbss_done:
+
+ lis sp,__stack@h
+ ori sp,sp,__stack@l
+
+ /* set up initial stack frame */
+ addi sp,sp,-4 /* make sure we don't overwrite debug mem */
+ lis r0,0
+ stw r0,0(sp) /* clear back chain */
+ stwu sp,-56(sp) /* push another stack frame */
+
+ li r3, 0 /* argc */
+ li r4, 0 /* argv */
+ li r5, 0 /* environp */
+
+ /* Let her rip */
+ bl FUNC_NAME(boot_card)
+
+ /*
+ * This should never get reached
+ */
+ /*
+ * Return MSR to its reset state
+ */
+ li r3,0
+ mtmsr r3
+ isync
+
+ /*
+ * Call reset entry point
+ */
+ lis r3,0xfff0
+ ori r3,r3,0x100
+ mtlr r3
+ blr
+.Lstart:
+ .size _start,.Lstart-_start
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/Makefile.in
new file mode 100644
index 0000000000..25464864d2
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/Makefile.in
@@ -0,0 +1,62 @@
+#
+# $Id:
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@:@srcdir@/../../../shared
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/startup.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=$(STARTUP_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=bsptrap
+S_FILES=$(S_PIECES:%=%.S)
+S_O_FILES=$(S_FILES:%.S=${ARCH}/%.o)
+
+SRCS=linkcmds $(C_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+# Files expected to be from the shared directory:
+# sbrk main bsplibc bsppost
+STARTUP_PIECES=bspstart bspclean sbrk setvec spurious genpvec swap \
+ main bsplibc bsppost
+
+#
+# (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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspclean.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspclean.c
new file mode 100644
index 0000000000..7a5db77049
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspclean.c
@@ -0,0 +1,30 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+/*
+ * bsp_cleanup()
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+
+extern void bsp_trap();
+
+void bsp_cleanup( void )
+{
+#if PPCN_60X_USE_DINK
+ bsp_trap();
+#endif
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspstart.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspstart.c
new file mode 100644
index 0000000000..e8ecd15472
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bspstart.c
@@ -0,0 +1,305 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+/* bspstart.c
+ *
+ * This set of routines starts the application. It includes application,
+ * board, and monitor specific initialization and configuration.
+ * The generic CPU dependent initialization has been performed
+ * before any of these are invoked.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#include <bsp.h>
+#include <pci.h>
+#include <rtems/libio.h>
+
+#include <libcsupport.h>
+
+unsigned char ucSystemType;
+unsigned char ucBoardRevMaj;
+unsigned char ucBoardRevMin;
+unsigned long ulMemorySize;
+unsigned long ulCpuBusClock;
+
+/*
+ * The bus speed is expressed in MHz
+ */
+static unsigned long ulBusSpeed[] = {
+ 56250000,
+ 60000000,
+ 64300000,
+ 66666667,
+ 75000000,
+ 83333333,
+ 100000000,
+ 66666667
+};
+
+/*
+ * The original 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;
+rtems_unsigned32 bsp_isr_level;
+
+static int stdin_fd, stdout_fd, stderr_fd;
+
+/*
+ * End of RTEMs image imported from linker
+ */
+extern int end;
+
+/*
+ * Use the shared implementations of the following routines
+ */
+
+void bsp_postdriver_hook(void);
+void bsp_libc_init( void *, unsigned32, int );
+
+/*
+ * bsp_pretasking_hook
+ *
+ * BSP pretasking hook. Called just before drivers are initialized.
+ * Used to setup libc and install any BSP extensions.
+ */
+
+void bsp_pretasking_hook(void)
+{
+ rtems_unsigned32 heap_start;
+ rtems_unsigned32 heap_size;
+
+ heap_start = (rtems_unsigned32) &end;
+ if (heap_start & (CPU_ALIGNMENT-1))
+ heap_start = (heap_start + CPU_ALIGNMENT) & ~(CPU_ALIGNMENT-1);
+
+ heap_size = BSP_Configuration.work_space_start - (void *)&end;
+ heap_size &= 0xfffffff0; /* keep it as a multiple of 16 bytes */
+
+ bsp_libc_init((void *) heap_start, heap_size, 0);
+
+ /*
+ * Initialise RTC hooks based on system type
+ */
+ InitializeRTC();
+
+ /*
+ * Initialise NvRAM hooks based on system type
+ */
+ InitializeNvRAM();
+
+ /*
+ * Initialise the PCI bus(ses)
+ */
+ InitializePCI();
+
+ /*
+ * Initialize the Universe PCI-VME bridge
+ */
+ InitializeUniverse();
+
+
+#ifdef RTEMS_DEBUG
+ rtems_debug_enable( RTEMS_DEBUG_ALL_MASK );
+#endif
+
+}
+
+/*
+ * bsp_std_close
+ *
+ * Simple routine to close all standard IO streams.
+ */
+
+void bsp_std_close( void )
+{
+ close(stdin_fd);
+ close(stdout_fd);
+ close(stderr_fd);
+}
+
+
+/*
+ * bsp_predriver_hook
+ *
+ * Before drivers are setup.
+ */
+void bsp_predriver_hook(void)
+{
+ /* bsp_spurious_initialize; ??*/
+ initialize_external_exception_vector();
+}
+
+/*
+ * bsp_start
+ *
+ * This routine does the bulk of the system initialization.
+ */
+
+void bsp_start( void )
+{
+ unsigned char *work_space_start;
+ unsigned char ucBoardRev, ucMothMemType, ucEquipPres1, ucEquipPres2;
+ unsigned16 usPVR=0;
+ unsigned8 ucTempl, ucTemph;
+ unsigned8 ucBanksPresent;
+ unsigned8 ucSimmPresent;
+ unsigned32 ulCurBank, ulTopBank;
+
+ /*
+ * Determine system type
+ */
+ inport_byte(&((PPLANARREGISTERS)0)->MotherboardMemoryType, ucMothMemType);
+ inport_byte(&((PPLANARREGISTERS)0)->SimmPresent, ucSimmPresent);
+
+ inport_byte(&((PPLANARREGISTERS)0)->EquipmentPresent1, ucEquipPres1);
+ inport_byte(&((PPLANARREGISTERS)0)->EquipmentPresent2, ucEquipPres2);
+ ucSystemType=((ucMothMemType&0x03)<<1) | ((ucEquipPres1&0x80)>>7);
+ ucSystemType^=7;
+
+ /*
+ * Determine board revision for use by rev. specific code
+ */
+ inport_byte(&((PPLANARREGISTERS)0)->BoardRevision, ucBoardRev);
+ ucBoardRevMaj=ucBoardRev>>5;
+ ucBoardRevMin=ucBoardRev&0x1f;
+
+ /*
+ * Determine the memory size by reading the end address for top
+ * assigned bank in the memory controller
+ */
+ (void)PCIConfigRead8(0,0,0,0xa0, &ucBanksPresent);
+ for(ulCurBank=0;ulCurBank<8;ulCurBank++)
+ {
+ if((ucBanksPresent>>ulCurBank)&0x01)
+ {
+ ulTopBank=ulCurBank;
+ }
+ }
+
+ (void)PCIConfigRead8(0,0,0,0x90+ulTopBank, &ucTempl);
+ (void)PCIConfigRead8(0,0,0,0x98+ulTopBank, &ucTemph);
+ ulMemorySize=(ucTempl+(ucTemph<<8)+1)<<20;
+#if PPCN_60X_USE_DINK
+ ulMemorySize=0x01fe0000;
+#endif
+
+ /*
+ * Determine processor bus clock
+ */
+ asm volatile ("mfpvr %0" : "=r" ((usPVR)) : "0" ((usPVR)));
+
+ /*
+ * Determine processor internal clock
+ */
+ if(ucSystemType==SYS_TYPE_PPC4)
+ {
+ if(((ucBoardRevMaj==1) && (ucBoardRevMin==0)) ||
+ ((ucSimmPresent&0x40)==0))
+ {
+ /*
+ * Rev. 1A is always 66MHz
+ */
+ ulCpuBusClock=66666667;
+ }
+ else
+ {
+ ulCpuBusClock=83333333;
+ }
+ }
+ else if((((usPVR>>16)==MPC603e) && (ucSystemType!=SYS_TYPE_PPC1)) ||
+ ((usPVR>>16)==MPC603ev) ||
+ ((usPVR>>16)==MPC604e))
+ {
+ ulCpuBusClock=ulBusSpeed[(ucEquipPres2&0x1c)>>2];
+ }
+ else
+ {
+ if(((ucSystemType>SYS_TYPE_PPC1) || (ucBoardRevMaj>=5)) &&
+ (ucEquipPres1&0x08))
+ {
+ /*
+ * 66 MHz bus clock for 005 if indicated
+ */
+ ulCpuBusClock=66666667;
+ }
+ else
+ {
+ /*
+ * 33 MHz bus clock for 004 always
+ */
+ ulCpuBusClock=33333333;
+ }
+ }
+
+
+ /*
+ * Allocate the memory for the RTEMS Work Space. This can come from
+ * a variety of places: hard coded address, malloc'ed from outside
+ * RTEMS world (e.g. simulator or primitive memory manager), or (as
+ * typically done by stock BSPs) by subtracting the required amount
+ * of work space from the last physical address on the CPU board.
+ */
+
+ work_space_start =
+ (unsigned char *)ulMemorySize - BSP_Configuration.work_space_size;
+
+ if ( work_space_start <= (unsigned char *)&end ) {
+ DEBUG_puts( "bspstart: Not enough RAM!!!\n" );
+ bsp_cleanup();
+ }
+
+ BSP_Configuration.work_space_start = work_space_start;
+
+ /*
+ * Add 1 region for RTEMS Malloc
+ */
+
+ BSP_Configuration.RTEMS_api_configuration->maximum_regions++;
+
+ /*
+ * Account for the console's resources
+ */
+
+ console_reserve_resources( &BSP_Configuration );
+
+ /*
+ * initialize the CPU table for this BSP
+ */
+
+ Cpu_table.exceptions_in_RAM = TRUE;
+ Cpu_table.pretasking_hook = bsp_pretasking_hook; /* init libc, etc. */
+ Cpu_table.predriver_hook = bsp_predriver_hook;
+ Cpu_table.postdriver_hook = bsp_postdriver_hook;
+ Cpu_table.do_zero_of_workspace = TRUE;
+ Cpu_table.interrupt_stack_size = (32 * 1024);
+ Cpu_table.clicks_per_usec = ulCpuBusClock/4000000;
+
+
+}
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bsptrap.S b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bsptrap.S
new file mode 100644
index 0000000000..3c6a4c16d4
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/bsptrap.S
@@ -0,0 +1,25 @@
+/*
+ * (c) 1998, Radstone Technology plc.
+ *
+ *
+ * This is an unpublished work the copyright in which vests
+ * in Radstone Technology plc. All rights reserved.
+ *
+ * The information contained herein is the property of Radstone
+ * Technology plc. and is supplied without liability for
+ * errors or omissions and no part may be reproduced, used or
+ * disclosed except as authorized by contract or other written
+ * permission. The copyright and the foregoing
+ * restriction on reproduction, use and disclosure extend to
+ * all the media in which this information may be
+ * embodied.
+ *
+ */
+#include <rtems/score/targopts.h>
+#include "ppc-asm.h"
+
+ .file "bsptrap.s"
+ .text
+FUNC_START(bsp_trap)
+ sc
+FUNC_END(bsp_trap)
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/genpvec.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/genpvec.c
new file mode 100644
index 0000000000..d4b8f46274
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/genpvec.c
@@ -0,0 +1,355 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+/* genpvec.c
+ *
+ * These routines handle the external exception. Multiple ISRs occur off
+ * of this one interrupt.
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#include <bsp.h>
+#include "chain.h"
+#include <assert.h>
+
+/*
+ * Proto types for this file
+ */
+
+rtems_isr external_exception_ISR (
+ rtems_vector_number vector /* IN */
+);
+
+#define NUM_LIRQ_HANDLERS 20
+#define NUM_LIRQ ( MAX_BOARD_IRQS - PPC_IRQ_LAST )
+
+/*
+ * Current 8259 masks
+ */
+unsigned8 ucMaster8259Mask;
+unsigned8 ucSlave8259Mask;
+
+/*
+ * Structure to for one of possible multiple interrupt handlers for
+ * a given interrupt.
+ */
+typedef struct
+{
+ Chain_Node Node;
+ rtems_isr_entry handler; /* isr routine */
+ rtems_vector_number vector; /* vector number */
+} EE_ISR_Type;
+
+
+/* Note: The following will not work if we add a method to remove
+ * handlers at a later time.
+ */
+ EE_ISR_Type ISR_Nodes [NUM_LIRQ_HANDLERS];
+ rtems_unsigned16 Nodes_Used;
+ Chain_Control ISR_Array [NUM_LIRQ];
+
+void initialize_external_exception_vector()
+{
+ rtems_isr_entry previous_isr;
+ rtems_status_code status;
+ int i;
+
+ Nodes_Used = 0;
+
+ for (i=0; i <NUM_LIRQ; i++)
+ {
+ Chain_Initialize_empty( &ISR_Array[i] );
+ }
+
+ /*
+ * Initialise the 8259s
+ */
+ outport_byte(ISA8259_M_CTRL, 0x11); /* ICW1 */
+ outport_byte(ISA8259_S_CTRL, 0x11); /* ICW1 */
+ outport_byte(ISA8259_M_MASK, 0x00); /* ICW2 vectors 0-7 */
+ outport_byte(ISA8259_S_MASK, 0x08); /* ICW2 vectors 8-15 */
+ outport_byte(ISA8259_M_MASK, 0x04); /* ICW3 cascade on IRQ2 */
+ outport_byte(ISA8259_S_MASK, 0x02); /* ICW3 cascade on IRQ2 */
+ outport_byte(ISA8259_M_MASK, 0x01); /* ICW4 x86 normal EOI */
+ outport_byte(ISA8259_S_MASK, 0x01); /* ICW4 x86 normal EOI */
+
+ /*
+ * Enable IRQ2 cascade and disable all other interrupts
+ */
+ ucMaster8259Mask=0xfb;
+ ucSlave8259Mask=0xff;
+
+ outport_byte(ISA8259_M_MASK, ucMaster8259Mask);
+ outport_byte(ISA8259_S_MASK, ucSlave8259Mask);
+
+ /*
+ * Set up edge/level
+ */
+ switch(ucSystemType)
+ {
+ case SYS_TYPE_PPC1:
+ {
+ if(ucBoardRevMaj<5)
+ {
+ outport_byte(ISA8259_S_ELCR,
+ ELCRS_INT15_LVL);
+ }
+ else
+ {
+ outport_byte(ISA8259_S_ELCR,
+ ELCRS_INT9_LVL |
+ ELCRS_INT11_LVL |
+ ELCRS_INT14_LVL |
+ ELCRS_INT15_LVL);
+ }
+ outport_byte(ISA8259_M_ELCR,
+ ELCRM_INT5_LVL |
+ ELCRM_INT7_LVL);
+ break;
+ }
+
+ case SYS_TYPE_PPC1a:
+ {
+ outport_byte(ISA8259_S_ELCR,
+ ELCRS_INT9_LVL |
+ ELCRS_INT11_LVL |
+ ELCRS_INT14_LVL |
+ ELCRS_INT15_LVL);
+ outport_byte(ISA8259_M_ELCR,
+ ELCRM_INT5_LVL);
+ break;
+ }
+
+ case SYS_TYPE_PPC2:
+ case SYS_TYPE_PPC2a:
+ case SYS_TYPE_PPC4:
+ default:
+ {
+ outport_byte(ISA8259_S_ELCR,
+ ELCRS_INT9_LVL |
+ ELCRS_INT10_LVL |
+ ELCRS_INT11_LVL |
+ ELCRS_INT14_LVL |
+ ELCRS_INT15_LVL);
+ outport_byte(ISA8259_M_ELCR,
+ ELCRM_INT5_LVL |
+ ELCRM_INT7_LVL);
+ break;
+ }
+ }
+
+ /*
+ * Install external_exception_ISR () as the handler for
+ * the General Purpose Interrupt.
+ */
+
+ status = rtems_interrupt_catch( external_exception_ISR,
+ PPC_IRQ_EXTERNAL,
+ (rtems_isr_entry *) &previous_isr );
+}
+
+/*
+ * This routine installs one of multiple ISRs for the general purpose
+ * inerrupt.
+ */
+void set_EE_vector(
+ rtems_isr_entry handler, /* isr routine */
+ rtems_vector_number vector /* vector number */
+)
+{
+ rtems_unsigned16 vec_idx = vector - PPCN_60X_8259_IRQ_BASE;
+ rtems_unsigned32 index;
+
+ assert (Nodes_Used < NUM_LIRQ_HANDLERS);
+
+ /*
+ * If we have already installed this handler for this vector, then
+ * just reset it.
+ */
+
+ for ( index=0 ; index < Nodes_Used ; index++ )
+ {
+ if(ISR_Nodes[index].vector == vector &&
+ ISR_Nodes[index].handler == handler)
+ {
+ return;
+ }
+ }
+
+ /*
+ * Doing things in this order makes them more atomic
+ */
+
+ Nodes_Used++;
+
+ index = Nodes_Used - 1;
+
+ ISR_Nodes[index].handler = handler;
+ ISR_Nodes[index].vector = vector;
+
+ Chain_Append( &ISR_Array[vec_idx], &ISR_Nodes[index].Node );
+
+ /*
+ * Enable the interrupt
+ */
+ En_Ext_Interrupt(vector);
+}
+
+/*
+ * This interrupt service routine is called for an External Exception.
+ */
+rtems_isr external_exception_ISR (
+ rtems_vector_number vector /* IN */
+)
+{
+ unsigned16 index;
+ unsigned8 ucISr;
+ EE_ISR_Type *node;
+
+ index = *((volatile unsigned8 *)IRQ_VECTOR_BASE);
+
+ /*
+ * check for spurious interrupt
+ */
+ if(index==7)
+ {
+ /*
+ * OCW3 select IS register
+ */
+ outport_byte(ISA8259_M_CTRL, 0x0b);
+ /*
+ * Read IS register
+ */
+ inport_byte(ISA8259_M_CTRL, ucISr);
+ if(!(ucISr & 0x80))
+ {
+ /*
+ * Spurious interrupt
+ */
+ return;
+ }
+ }
+
+ node=(EE_ISR_Type *)ISR_Array[index].first;
+ while(!_Chain_Is_tail(&ISR_Array[index], (Chain_Node *)node))
+ {
+ (*node->handler)( node->vector );
+ node = (EE_ISR_Type *)node->Node.next;
+ }
+
+ /*
+ * Dismiss the interrupt
+ */
+ if(index&8)
+ {
+ /*
+ * Dismiss the interrupt in Slave first as it
+ * is cascaded
+ */
+ outport_byte(ISA8259_S_CTRL, NONSPECIFIC_EOI);
+ }
+
+ /*
+ * Dismiss the interrupt in Master
+ */
+ outport_byte(ISA8259_M_CTRL, NONSPECIFIC_EOI);
+}
+
+void Dis_Ext_Interrupt(int level)
+{
+ ISR_Level Irql;
+
+ level-=PPCN_60X_8259_IRQ_BASE;
+
+ if(level==2)
+ {
+ /*
+ * Level 2 is for cascade and must not be fiddled with
+ */
+ return;
+ }
+
+ /*
+ * Ensure that accesses to the mask are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ if(level<8)
+ {
+ /*
+ * Interrupt is handled by Master
+ */
+ ucMaster8259Mask|=1<<level;
+ outport_byte(ISA8259_M_MASK, ucMaster8259Mask);
+ }
+ else
+ {
+ /*
+ * Interrupt is handled by Slave
+ */
+ ucSlave8259Mask|=1<<(level-8);
+ outport_byte(ISA8259_S_MASK, ucSlave8259Mask);
+ }
+ _ISR_Enable(Irql);
+}
+
+void En_Ext_Interrupt(int level)
+{
+ ISR_Level Irql;
+
+ level-=PPCN_60X_8259_IRQ_BASE;
+
+ if(level==2)
+ {
+ /*
+ * Level 2 is for cascade and must not be fiddled with
+ */
+ return;
+ }
+
+ /*
+ * Ensure that accesses to the mask are indivisible
+ */
+ _ISR_Disable(Irql);
+
+ if(level<8)
+ {
+ /*
+ * Interrupt is handled by Master
+ */
+ ucMaster8259Mask&=~(1<<level);
+ outport_byte(ISA8259_M_MASK, ucMaster8259Mask);
+ }
+ else
+ {
+ /*
+ * Interrupt is handled by Slave
+ */
+ ucSlave8259Mask&=~(1<<(level-8));
+ outport_byte(ISA8259_S_MASK, ucSlave8259Mask);
+ }
+
+ _ISR_Enable(Irql);
+}
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/linkcmds b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/linkcmds
new file mode 100644
index 0000000000..7f4f3cf330
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/linkcmds
@@ -0,0 +1,173 @@
+OUTPUT_FORMAT("elf32-powerpc", "elf32-powerpc",
+ "elf32-powerpc")
+
+OUTPUT_ARCH(powerpc)
+ENTRY(_start)
+
+/*
+ * Number of Decrementer countdowns per millisecond
+ *
+ * Calculated by: (66.67 Mhz * 1000) / 4 cycles per click
+ */
+
+SECTIONS
+{
+ .vectors 0x00100 :
+ {
+ *(.vectors)
+ }
+
+ /* Read-only sections, merged into text segment: */
+ /* SDS ROM worked at 0x30000 */
+ . = 0x30000;
+ .interp : { *(.interp) }
+ .hash : { *(.hash) }
+ .dynsym : { *(.dynsym) }
+ .dynstr : { *(.dynstr) }
+ .rela.text : { *(.rela.text) }
+ .rela.data : { *(.rela.data) }
+ .rela.rodata : { *(.rela.rodata) }
+ .rela.got : { *(.rela.got) }
+ .rela.got1 : { *(.rela.got1) }
+ .rela.got2 : { *(.rela.got2) }
+ .rela.ctors : { *(.rela.ctors) }
+ .rela.dtors : { *(.rela.dtors) }
+ .rela.init : { *(.rela.init) }
+ .rela.fini : { *(.rela.fini) }
+ .rela.bss : { *(.rela.bss) }
+ .rela.plt : { *(.rela.plt) }
+ .rela.sdata : { *(.rela.sdata2) }
+ .rela.sbss : { *(.rela.sbss2) }
+ .rela.sdata2 : { *(.rela.sdata2) }
+ .rela.sbss2 : { *(.rela.sbss2) }
+ .plt : { *(.plt) }
+ .text :
+ {
+ *(.text)
+ *(.descriptors)
+ /* .gnu.warning sections are handled specially by elf32.em. */
+ *(.gnu.warning)
+ } =0
+ .init : { *(.init) } =0
+ .fini : { *(.fini) } =0
+ .rodata : { *(.rodata) }
+ .rodata1 : { *(.rodata1) }
+ _etext = .;
+ PROVIDE (etext = .);
+ PROVIDE (__SDATA2_START__ = .);
+ .sdata2 : { *(.sdata2) }
+ PROVIDE (__SBSS2_START__ = .);
+ .sbss2 : { *(.sbss2) }
+ PROVIDE (__SBSS2_END__ = .);
+ /* Adjust the address for the data segment. We want to adjust up to
+ the same address within the page on the next page up. It would
+ be more correct to do this:
+ . = ALIGN(0x40000) + (ALIGN(8) & (0x40000 - 1));
+ The current expression does not correctly handle the case of a
+ text segment ending precisely at the end of a page; it causes the
+ data segment to skip a page. The above expression does not have
+ this problem, but it will currently (2/95) cause BFD to allocate
+ a single segment, combining both text and data, for this case.
+ This will prevent the text segment from being shared among
+ multiple executions of the program; I think that is more
+ important than losing a page of the virtual address space (note
+ that no actual memory is lost; the page which is skipped can not
+ be referenced). */
+ . = ALIGN(8) + 0x40000;
+ PROVIDE (sdata = .);
+ .data :
+ {
+ *(.data)
+ CONSTRUCTORS
+ }
+ PROVIDE (__EXCEPT_START__ = .);
+ .gcc_except_table : { *(.gcc_except_table) }
+ PROVIDE (__EXCEPT_END__ = .);
+
+ .data1 : { *(.data1) }
+ .got1 : { *(.got1) }
+ .dynamic : { *(.dynamic) }
+ /* Put .ctors and .dtors next to the .got2 section, so that the pointers
+ get relocated with -mrelocatable. Also put in the .fixup pointers.
+ The current compiler no longer needs this, but keep it around for 2.7.2 */
+ PROVIDE (_GOT2_START_ = .);
+ .got2 : { *(.got2) }
+ PROVIDE (__GOT2_END__ = .);
+ PROVIDE (__CTOR_LIST__ = .);
+ .ctors : { *(.ctors) }
+ PROVIDE (__CTOR_END__ = .);
+ PROVIDE (__DTOR_LIST__ = .);
+ .dtors : { *(.dtors) }
+ PROVIDE (__DTOR_END__ = .);
+ PROVIDE (_FIXUP_START_ = .);
+ .fixup : { *(.fixup) }
+ PROVIDE (_FIXUP_END_ = .);
+ PROVIDE (__FIXUP_END__ = .);
+ PROVIDE (_GOT2_END_ = .);
+ PROVIDE (_GOT_START_ = .);
+ s.got = .;
+ .got : { *(.got) }
+ .got.plt : { *(.got.plt) }
+ PROVIDE (_GOT_END_ = .);
+ PROVIDE (__GOT_END__ = .);
+ /* We want the small data sections together, so single-instruction offsets
+ can access them all, and initialized data all before uninitialized, so
+ we can shorten the on-disk segment size. */
+ PROVIDE (__SDATA_START__ = .);
+ .sdata : { *(.sdata) }
+ _edata = .;
+ PROVIDE (edata = .);
+ . = ALIGN(8) + 0x1000;
+ PROVIDE (__SBSS_START__ = .);
+ .sbss :
+ {
+ PROVIDE (__sbss_start = .);
+ *(.sbss)
+ *(.scommon)
+ PROVIDE (__sbss_end = .);
+ }
+ PROVIDE (__SBSS_END__ = .);
+ .bss :
+ {
+ PROVIDE (__bss_start = .);
+ *(.dynbss)
+ *(.bss)
+ *(COMMON)
+ PROVIDE (__bss_end = .);
+ }
+ . = ALIGN(8) + 0x8000;
+ PROVIDE (__stack = .);
+ _end = . ;
+ PROVIDE (end = .);
+
+ /* These are needed for ELF backends which have not yet been
+ converted to the new style linker. */
+ .stab 0 : { *(.stab) }
+ .stabstr 0 : { *(.stabstr) }
+ /* DWARF debug sections.
+ Symbols in the DWARF debugging sections are relative to the beginning
+ of the section so we begin them at 0. */
+ /* DWARF 1 */
+ .debug 0 : { *(.debug) }
+ .line 0 : { *(.line) }
+ /* GNU DWARF 1 extensions */
+ .debug_srcinfo 0 : { *(.debug_srcinfo) }
+ .debug_sfnames 0 : { *(.debug_sfnames) }
+ /* DWARF 1.1 and DWARF 2 */
+ .debug_aranges 0 : { *(.debug_aranges) }
+ .debug_pubnames 0 : { *(.debug_pubnames) }
+ /* DWARF 2 */
+ .debug_info 0 : { *(.debug_info) }
+ .debug_abbrev 0 : { *(.debug_abbrev) }
+ .debug_line 0 : { *(.debug_line) }
+ .debug_frame 0 : { *(.debug_frame) }
+ .debug_str 0 : { *(.debug_str) }
+ .debug_loc 0 : { *(.debug_loc) }
+ .debug_macinfo 0 : { *(.debug_macinfo) }
+ /* SGI/MIPS DWARF 2 extensions */
+ .debug_weaknames 0 : { *(.debug_weaknames) }
+ .debug_funcnames 0 : { *(.debug_funcnames) }
+ .debug_typenames 0 : { *(.debug_typenames) }
+ .debug_varnames 0 : { *(.debug_varnames) }
+ /* These must appear regardless of . */
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/rtems-ctor.cc b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/rtems-ctor.cc
new file mode 100644
index 0000000000..1949e71f0c
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/rtems-ctor.cc
@@ -0,0 +1,124 @@
+/*
+ * rtems-ctor.cc
+ *
+ * Description:
+ * This file exists solely to (try to) ensure RTEMS is initialized
+ * before any global constructors are run.
+ *
+ * The problem:
+ * Global constructors might reasonably expect that new() will
+ * work, but since new() uses malloc() which uses RTEMS regions,
+ * it can not be called until after initialize_executive().
+ *
+ * Global constructors are called in GNU systems one of 2 ways:
+ *
+ * an "invisible" call to __main() inserted by compiler
+ * This __main() calls __do_global_ctors() which
+ * walks thru the table and calls all global
+ * constructors.
+ *
+ * or -
+ * A special section is put into the linked binary. The
+ * system startup code knows to run the constructors in
+ * this special section before calling main().
+ *
+ * By making RTEMS initialization a constructor, we avoid having
+ * too much about all this. All we have to guarantee is that
+ * this constructor is the first one run.
+ *
+ *
+ * So for the first case above, this is what happens
+ *
+ * host crt0
+ * main()
+ * __main()
+ * __do_global_ctors()
+ * bsp_start()
+ * init_executive_early()
+ * <<any other constructors>>
+ *
+ * rtems_init_executive_late()
+ * bsp_cleanup()
+ *
+ * TODO:
+ *
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#include <bsp.h>
+
+/*
+ * RTEMS program name
+ * Probably not used by anyone, but it is nice to have it.
+ * Actually the UNIX version of CPU_INVOKE_DEBUGGER will probably
+ * need to use it
+ */
+
+char *rtems_progname;
+char **rtems_environp;
+
+#ifdef USE_CONSTRUCTORS_FOR_INIT_EXEC
+
+class RTEMS {
+ public:
+ RTEMS();
+ ~RTEMS();
+};
+
+RTEMS rtems_constructor;
+
+RTEMS::RTEMS()
+{
+ bsp_start();
+}
+
+RTEMS::~RTEMS()
+{
+ bsp_cleanup();
+}
+#endif
+
+extern "C" {
+ int
+ main(int argc,
+ char **argv,
+ char **environp)
+ {
+
+#ifndef USE_CONSTRUCTORS_FOR_INIT_EXEC
+ bsp_start();
+#endif
+
+ if ((argc > 0) && argv && argv[0])
+ rtems_progname = argv[0];
+ else
+ rtems_progname = "RTEMS";
+
+ rtems_environp = environp;
+
+ /*
+ * Start multitasking
+ */
+ rtems_initialize_executive_late( bsp_isr_level );
+
+#ifndef USE_CONSTRUCTORS_FOR_INIT_EXEC
+ bsp_cleanup();
+#endif
+
+ /*
+ * Returns when multitasking is stopped
+ * This allows our destructors to get run normally
+ */
+
+ return 0;
+ }
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/setvec.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/setvec.c
new file mode 100644
index 0000000000..dd7c39da82
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/setvec.c
@@ -0,0 +1,55 @@
+/* set_vector
+ *
+ * This routine installs an interrupt vector on the target Board/CPU.
+ * This routine is allowed to be as board dependent as necessary.
+ *
+ * INPUT:
+ * handler - interrupt handler entry point
+ * vector - vector number
+ * type - 0 indicates raw hardware connect
+ * 1 indicates RTEMS interrupt connect
+ *
+ * RETURNS:
+ * address of previous interrupt handler
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id:
+ */
+
+#include <rtems.h>
+#include <bsp.h>
+
+
+/*
+ * This routine installs vector number vector.
+ *
+ */
+rtems_isr_entry set_vector( /* returns old vector */
+ rtems_isr_entry handler, /* isr routine */
+ rtems_vector_number vector, /* vector number */
+ int type /* RTEMS or RAW intr */
+)
+{
+ rtems_isr_entry previous_isr;
+ rtems_status_code status;
+
+ /*
+ * vectors greater than PPC_IRQ_LAST are handled by the General purpose
+ * interupt handler. (8259)
+ */
+ if ( vector > PPC_IRQ_LAST ) {
+ set_EE_vector ( handler, vector );
+ }
+ else {
+ status = rtems_interrupt_catch
+ ( handler, vector, (rtems_isr_entry *) &previous_isr );
+ }
+ return previous_isr;
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/spurious.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/spurious.c
new file mode 100644
index 0000000000..af18752c71
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/spurious.c
@@ -0,0 +1,202 @@
+/*
+ * PPCn_60x Spurious Trap Handler
+ *
+ * This is just enough of a trap handler to let us know what
+ * the likely source of the trap was.
+ *
+ * Based upon the SPARC ERC32 version which was developed as
+ * part of the port of RTEMS to the ERC32 implementation
+ * of the SPARC by On-Line Applications Research Corporation (OAR)
+ * under contract to the European Space Agency (ESA).
+ *
+ * COPYRIGHT (c) 1995. European Space Agency.
+ *
+ * This terms of the RTEMS license apply to this file.
+ *
+ * $Id$
+ */
+
+#include <bsp.h>
+
+#include <string.h>
+
+static const char digits[16] = "0123456789abcdef";
+
+rtems_isr bsp_stub_handler(
+ rtems_vector_number trap
+)
+{
+}
+
+/*
+ * bsp_spurious_handler
+ *
+ * Print a message on the debug console and then die
+ */
+rtems_isr bsp_spurious_handler(
+ rtems_vector_number trap
+)
+{
+
+
+
+ DEBUG_puts( "Spurious Trap" );
+
+ switch ( trap ) {
+ case PPC_IRQ_SYSTEM_RESET:
+ DEBUG_puts( "System reset" );
+ break;
+ case PPC_IRQ_MCHECK:
+ DEBUG_puts( "Machine check" );
+ break;
+ case PPC_IRQ_PROTECT:
+ DEBUG_puts( "DSI" );
+ break;
+ case PPC_IRQ_ISI:
+ DEBUG_puts( "ISI" );
+ break;
+ case PPC_IRQ_EXTERNAL:
+ DEBUG_puts( "External interupt" );
+ break;
+ case PPC_IRQ_ALIGNMENT:
+ DEBUG_puts( "Alignment Exception" );
+ break;
+ case PPC_IRQ_PROGRAM:
+ DEBUG_puts( "Program" );
+ break;
+ case PPC_IRQ_NOFP:
+ DEBUG_puts( "Floating point unavailable" );
+ break;
+ case PPC_IRQ_DECREMENTER:
+ DEBUG_puts( "Decrementer" );
+ break;
+ case PPC_IRQ_RESERVED_A:
+ DEBUG_puts( "Reserved 0x00a00" );
+ break;
+ case PPC_IRQ_RESERVED_B:
+ DEBUG_puts( "Reserved 0x00b00" );
+ break;
+ case PPC_IRQ_SCALL:
+ DEBUG_puts( "System call" );
+ break;
+ case PPC_IRQ_TRACE:
+ DEBUG_puts( "Trace" );
+ break;
+ case PPC_IRQ_FP_ASST:
+ DEBUG_puts( "Floating point Assist" );
+ break;
+
+#if defined(ppc403)
+#error "Please fill in names. "
+ case PPC_IRQ_CRIT :
+ DEBUG_puts( "Critical Error ");
+ break;
+ case PPC_IRQ_PIT:
+ DEBUG_puts( "0x01000" );
+ break;
+ case PPC_IRQ_FIT:
+ DEBUG_puts( "0x01010" );
+ break;
+ case PPC_IRQ_WATCHDOG :
+ DEBUG_puts( "0x01020" );
+ break;
+ case PPC_IRQ_DEBUG :
+ DEBUG_puts( "0x02000" );
+ break;
+
+#elif defined(ppc601)
+#error "Please fill in names. "
+ case PPC_IRQ_TRACE :
+ DEBUG_puts( "0x02000" );
+ break;
+
+#elif defined(ppc603)
+#error "Please fill in names. "
+ case PPC_IRQ_TRANS_MISS :
+ DEBUG_puts( "0x1000" );
+ break;
+ case PPC_IRQ_DATA_LOAD:
+ DEBUG_puts( "0x1100" );
+ break;
+ case PPC_IRQ_DATA_STORE:
+ DEBUG_puts( "0x1200" );
+ break;
+ case PPC_IRQ_ADDR_BRK:
+ DEBUG_puts( "0x1300" );
+ break;
+ case PPC_IRQ_SYS_MGT:
+ DEBUG_puts( "0x1400" );
+ break;
+
+#elif defined(ppc603e)
+ case PPC_TLB_INST_MISS:
+ DEBUG_puts( "Instruction Translation Miss" );
+ break;
+ case PPC_TLB_LOAD_MISS:
+ DEBUG_puts( "Data Load Translation Miss" );
+ break;
+ case PPC_TLB_STORE_MISS :
+ DEBUG_puts( "Data store Translation Miss");
+ break;
+ case PPC_IRQ_ADDRBRK:
+ DEBUG_puts( "Instruction address break point" );
+ break;
+ case PPC_IRQ_SYS_MGT:
+ DEBUG_puts( "System management interrupt" );
+ break;
+
+#elif defined(ppc604)
+#error "Please fill in names. "
+ case PPC_IRQ_ADDR_BRK:
+ DEBUG_puts( "0x1300" );
+ break;
+ case PPC_IRQ_SYS_MGT:
+ DEBUG_puts( "0x1400" );
+ break;
+#endif
+
+ default:
+ DEBUG_puts( "Undefined exception " );
+ break;
+ }
+
+ /*
+ * What else can we do but stop ...
+ */
+ /*
+ asm volatile( "" );
+ */
+}
+
+/*
+ * bsp_spurious_initialize
+ *
+ * Install the spurious handler for most traps.
+ */
+
+void bsp_spurious_initialize()
+{
+ rtems_unsigned32 trap;
+
+ for ( trap=0 ; trap < PPC_IRQ_LAST ; trap++ ) {
+
+ /*
+ * Skip window overflow, underflow, and flush as well as software
+ * trap 0 which we will use as a shutdown.
+ */
+
+ set_vector( bsp_spurious_handler, trap, 1 );
+ }
+
+ set_vector( bsp_stub_handler, PPC_IRQ_DECREMENTER, 1 );
+ set_vector( bsp_stub_handler, PPC_IRQ_TRACE, 1 );
+ set_vector( bsp_stub_handler, PPC_IRQ_SYS_MGT, 1 );
+}
+
+
+
+
+
+
+
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/startup/swap.c b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/swap.c
new file mode 100644
index 0000000000..58b3e13dbb
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/startup/swap.c
@@ -0,0 +1,64 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#include <rtems.h>
+
+/*
+ * JRS - February 20, 1998
+ *
+ * There is a swap32 in each port. So this should be removed.
+ *
+ * Adding a swap16 to the port would be useful.
+ *
+ * The end of all this would be to remove this file.
+ */
+
+inline unsigned int Swap32(
+ unsigned32 ulValue
+)
+{
+ unsigned32 ulSwapped;
+
+ asm volatile(
+ "rlwimi %0,%1,8,24,31;"
+ "rlwimi %0,%1,24,16,23;"
+ "rlwimi %0,%1,8,8,15;"
+ "rlwimi %0,%1,24,0,7;" :
+
+ "=&r" ((ulSwapped)) :
+ "r" ((ulValue))
+ );
+
+ return( ulSwapped );
+}
+
+inline unsigned int Swap16(
+ unsigned16 usValue
+)
+{
+ unsigned16 usSwapped;
+
+ asm volatile(
+ "rlwimi %0,%1,24,24,31;"
+ "rlwimi %0,%1,8,16,23;" :
+
+ "=&r" ((usSwapped)) :
+ "r" ((usValue))
+ );
+
+ return( usSwapped );
+}
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/timer/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/timer/Makefile.in
new file mode 100644
index 0000000000..16665e4de9
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/timer/Makefile.in
@@ -0,0 +1,59 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+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=
+S_FILES=$(S_PIECES:%=%.s)
+S_O_FILES=$(S_FILES:%.s=${ARCH}/%.o)
+
+SRCS=$(C_FILES) $(CC_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/timer/timer.c b/c/src/lib/libbsp/powerpc/ppcn_60x/timer/timer.c
new file mode 100644
index 0000000000..c96587a233
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/timer/timer.c
@@ -0,0 +1,82 @@
+/* timer.c
+ *
+ * This file implements a benchmark timer using the General Purpose Timer.
+ *
+ * Notes:
+ *
+ * BSP_TIMER_AVG_OVERHEAD and BSP_TIMER_LEAST_VALID are required to be
+ * provided in bsp.h
+ *
+ * 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 in
+ * the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#include <assert.h>
+
+#include <bsp.h>
+
+rtems_unsigned64 Timer_driver_Start_time;
+
+rtems_boolean Timer_driver_Find_average_overhead;
+
+/*
+ * Timer_initialize
+ */
+void Timer_initialize()
+{
+
+ /*
+ * Timer runs long and accurate enough not to require an interrupt.
+ */
+
+ Timer_driver_Start_time = PPC_Get_timebase_register();
+}
+
+/*
+ * Read_timer
+ */
+int Read_timer()
+{
+ rtems_unsigned64 clicks;
+ rtems_unsigned64 total64;
+ rtems_unsigned32 total;
+
+ /* approximately CLOCK_SPEED clicks per microsecond */
+
+ clicks = PPC_Get_timebase_register();
+
+ assert( clicks > Timer_driver_Start_time );
+
+ total64 = clicks - Timer_driver_Start_time;
+
+ assert( total64 <= 0xffffffff ); /* fits into a unsigned32 */
+
+ total = (rtems_unsigned32) total64;
+
+ if ( Timer_driver_Find_average_overhead == 1 )
+ return total; /* in "clicks" of the decrementer units */
+
+ if ( total < BSP_TIMER_LEAST_VALID )
+ return 0; /* below timer resolution */
+
+ return BSP_Convert_decrementer(total - BSP_TIMER_AVG_OVERHEAD);
+}
+
+rtems_status_code Empty_function( void )
+{
+ return RTEMS_SUCCESSFUL;
+}
+
+void Set_find_average_overhead(
+ rtems_boolean find_flag
+)
+{
+ Timer_driver_Find_average_overhead = find_flag;
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/tod/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/Makefile.in
new file mode 100644
index 0000000000..240373136e
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/Makefile.in
@@ -0,0 +1,56 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/tod.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=$(TOD_PIECES)
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_ROOT)/make/leaf.cfg
+
+TOD_PIECES=tod
+
+#
+# (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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/tod/cmos.h b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/cmos.h
new file mode 100644
index 0000000000..92cd7813a8
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/cmos.h
@@ -0,0 +1,95 @@
+/* Structure map for CMOS on PowerPC Reference Platform */
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+/* CMOS is the 64 bytes of RAM in the DS1385 chip */
+/* The CRC's are computed with x**16+x**12+x**5 + 1 polynomial */
+/* The clock is kept in 24 hour BCD mode and should be set to UT(GMT) */
+
+#ifndef _CMOS_
+#define _CMOS_
+
+/*
+ * Address port is at 0x70, data at 0x71
+ */
+#define RTC_PORT 0x70
+
+/* Define Realtime Clock register numbers. */
+
+#define RTC_SECOND 0 /* second of minute [0..59] */
+#define RTC_SECOND_ALARM 1 /* seconds to alarm */
+#define RTC_MINUTE 2 /* minute of hour [0..59] */
+#define RTC_MINUTE_ALARM 3 /* minutes to alarm */
+#define RTC_HOUR 4 /* hour of day [0..23] */
+#define RTC_HOUR_ALARM 5 /* hours to alarm */
+#define RTC_DAY_OF_WEEK 6 /* day of week [1..7] */
+#define RTC_DAY_OF_MONTH 7 /* day of month [1..31] */
+#define RTC_MONTH 8 /* month of year [1..12] */
+#define RTC_YEAR 9 /* year [00..99] */
+#define RTC_CONTROL_REGISTERA 10 /* control register A */
+#define RTC_CONTROL_REGISTERB 11 /* control register B */
+#define RTC_CONTROL_REGISTERC 12 /* control register C */
+#define RTC_CONTROL_REGISTERD 13 /* control register D */
+#define RTC_BATTERY_BACKED_UP_RAM 14 /* battery backed up RAM [0..49] */
+
+/* Define Control Register A structure. */
+#define DS1385_REGA_UIP 0x80
+
+/* Define Control Register B structure. */
+#define DS1385_REGB_SET_TIME 0x80
+#define DS1385_REGB_TIM_IRQ_EN 0x40
+#define DS1385_REGB_ALM_IRQ_EN 0x20
+#define DS1385_REGB_UPD_IRQ_EN 0x10
+#define DS1385_REGB_SQR_EN 0x08
+#define DS1385_REGB_DATA_M 0x04
+#define DS1385_REGB_HOURS_FMT 0x02
+#define DS1385_REGB_DLS_EN 0x01
+
+/* Define Control Register C structure. */
+#define DS1385_REGC_IRQ_REQ 0x08
+#define DS1385_REGC_IRQ_TIME 0x04
+#define DS1385_REGC_IRQ_ALM 0x02
+#define DS1385_REGC_IRQ_UPD 0x01
+
+/* Define Control Register D structure. */
+#define DS1385_REGD_VALID 0x80
+
+typedef struct _CMOS_MAP {
+ volatile rtems_unsigned8 DateAndTime[14];
+
+ rtems_unsigned8 SystemDependentArea1[2];
+ rtems_unsigned8 SystemDependentArea2[8];
+ rtems_unsigned8 FeatureByte0[1];
+ rtems_unsigned8 FeatureByte1[1]; /* 19 = PW Flag;
+ attribute = write protect */
+ rtems_unsigned8 Century[1]; /* century byte in BCD, e.g. 0x19 currently */
+ rtems_unsigned8 FeatureByte3[1];
+ rtems_unsigned8 FeatureByte4[1];
+ rtems_unsigned8 FeatureByte5[1];
+ rtems_unsigned8 FeatureByte6[1];
+ rtems_unsigned8 FeatureByte7[1]; /* 1F = Alternate PW Flag;
+ attribute = write protect */
+ rtems_unsigned8 BootPW[14]; /* Power-on password needed to boot system;
+ reset value = 0x00000000000000005a5a5a5a5a5a);
+ attribute = lock */
+ rtems_unsigned8 BootCrc[2]; /* CRC on BootPW */
+ rtems_unsigned8 ConfigPW[14]; /* Configuration Password needed to
+ change configuration of system;
+ reset value = 0x00000000000000005a5a5a5a5a5a);
+ attribute = lock */
+ rtems_unsigned8 ConfigCrc[2]; /* CRC on ConfigPW */
+} CMOS_MAP, *PCMOS_MAP;
+
+#endif /* _CMOS_ */
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/tod/tod.c b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/tod.c
new file mode 100644
index 0000000000..80e0ff3116
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/tod/tod.c
@@ -0,0 +1,617 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ */
+
+#define MIN_YEAR 1996
+
+#include <stdlib.h>
+#include "bsp.h"
+#include "cmos.h"
+#include "../nvram/mk48t18.h"
+
+#define Bin2BCD(Value) (((Value / 10) << 4) | (Value % 10))
+#define BCD2Bin(BcdValue) ((BcdValue >> 4) * 10 + (BcdValue & 0x0f))
+
+/*
+ * Private types
+ */
+typedef
+void
+(*PTIMESET)
+(
+ rtems_time_of_day *pTOD
+);
+
+typedef
+boolean
+(*PTIMEGET)
+(
+ rtems_time_of_day *pTOD
+);
+
+typedef struct _TIME_ENTRY_TABLE
+{
+ PTIMESET SetTime;
+ PTIMEGET GetTime;
+} TIME_ENTRY_TABLE, *PTIME_ENTRY_TABLE;
+
+/*
+ * Private routines
+ */
+
+/*
+ * DS1385 specific routines
+ */
+static void timeDsSet(rtems_time_of_day *pTOD);
+static boolean timeDsGet(rtems_time_of_day *pTOD);
+
+/*
+ * MK48T18 specific routines
+ */
+static void timeMkSet(rtems_time_of_day *pTOD);
+static boolean timeMkGet(rtems_time_of_day *pTOD);
+
+TIME_ENTRY_TABLE timeDsTable =
+{
+ timeDsSet,
+ timeDsGet
+};
+
+TIME_ENTRY_TABLE timeMkTable =
+{
+ timeMkSet,
+ timeMkGet
+};
+
+/*
+ * Private variables
+ */
+static PTIME_ENTRY_TABLE pTimeFunc;
+
+/*
+ * Mutual-exclusion semaphore
+ */
+static rtems_id semRTC;
+
+/*
+ * This only works for the Gregorian calendar - i.e. after 1752 (in the UK)
+ */
+rtems_unsigned8
+GregorianDay(rtems_time_of_day *pTOD)
+{
+ boolean isLeap;
+ unsigned long leapsToDate;
+ unsigned long lastYear;
+ unsigned long day;
+ unsigned long MonthOffset[] = { 0, 31, 59, 90, 120, 151,
+ 181, 212, 243, 273, 304, 334 };
+
+ lastYear=pTOD->year-1;
+
+ /*
+ * Number of leap corrections to apply up to end of last year
+ */
+ leapsToDate = lastYear/4 - lastYear/100 + lastYear/400;
+
+ /*
+ * This year is a leap year if it is divisible by 4 except when it is
+ * divisible by 100 unless it is divisible by 400
+ *
+ * e.g. 1904 was a leap year, 1900 was not, 1996 is, and 2000 will be
+ */
+ isLeap = (pTOD->year%4==0) &&
+ ((pTOD->year%100!=0) || (pTOD->year%400==0));
+
+ if(isLeap && (pTOD->month>2))
+ {
+ day=1;
+ }
+ else
+ {
+ day=0;
+ }
+
+ day += lastYear*365 + leapsToDate + MonthOffset[pTOD->month-1] +
+ pTOD->day;
+
+ return((rtems_unsigned8)(day%7));
+}
+
+void
+DsWriteRawClockRegister (
+ rtems_unsigned8 Register,
+ rtems_unsigned8 Value
+)
+
+/*++
+
+Routine Description:
+
+ This routine reads the specified realtime clock register.
+
+ This function was added to bridge the BCD format of the IBM roms
+ and the binary formate of NT
+
+
+Arguments:
+
+ Register - Supplies the number of the register whose value is read.
+
+Return Value:
+
+ The value of the register is returned as the function value.
+
+--*/
+
+{
+ outport_byte((rtems_unsigned8 *)RTC_PORT, Register & 0x7f);
+
+ /* Read the realtime clock register value. */
+
+ outport_byte((rtems_unsigned8 *)(RTC_PORT + 1), Value);
+ return;
+}
+
+rtems_unsigned8
+DsReadRawClockRegister (
+ rtems_unsigned8 Register
+)
+
+/*++
+
+Routine Description:
+
+ This routine reads the specified realtime clock register.
+
+ This function was added to bridge the BCD format of the IBM roms
+ and the binary formate of NT
+
+
+Arguments:
+
+ Register - Supplies the number of the register whose value is read.
+
+Return Value:
+
+ The value of the register is returned as the function value.
+
+--*/
+
+{
+ rtems_unsigned8 ucDataByte;
+
+ outport_byte((rtems_unsigned8 *)RTC_PORT, Register & 0x7f);
+
+ /* Read the realtime clock register value. */
+
+ inport_byte((rtems_unsigned8 *)(RTC_PORT + 1), ucDataByte);
+ return ucDataByte;
+}
+
+void
+DsWriteClockRegister (
+ rtems_unsigned8 Register,
+ rtems_unsigned8 Value
+)
+
+/*++
+
+Routine Description:
+
+ This routine writes the specified value to the specified realtime
+ clock register.
+
+Arguments:
+
+ Register - Supplies the number of the register whose value is written.
+
+ Value - Supplies the value that is written to the specified register.
+
+Return Value:
+
+ The value of the register is returned as the function value.
+
+--*/
+
+{
+ rtems_unsigned8 BcdValue;
+
+ BcdValue = Bin2BCD(Value);
+ DsWriteRawClockRegister(Register, BcdValue);
+ return;
+}
+
+rtems_unsigned8
+DsReadClockRegister (
+ rtems_unsigned8 Register
+)
+
+/*++
+
+Routine Description:
+
+ This routine reads the specified realtime clock register.
+
+Arguments:
+
+ Register - Supplies the number of the register whose value is read.
+
+Return Value:
+
+ The value of the register is returned as the function value.
+
+--*/
+
+{
+ rtems_unsigned8 BcdValue;
+
+ BcdValue = DsReadRawClockRegister(Register);
+ return BCD2Bin(BcdValue);
+}
+
+void
+timeDsSet (
+ rtems_time_of_day *pTOD
+ )
+
+/*++
+
+Routine Description:
+
+ This routine sets the realtime clock.
+
+ N.B. This routine assumes that the caller has provided any required
+ synchronization to set the realtime clock information.
+
+Arguments:
+
+ pTOD - Supplies a pointer to a time structure that specifies the
+ realtime clock information.
+
+Return Value:
+
+ If the power to the realtime clock has not failed, then the time
+ values are written to the realtime clock and a value of TRUE is
+ returned. Otherwise, a value of FALSE is returned.
+
+--*/
+
+{
+ rtems_unsigned8 ucDataByte;
+ PCMOS_MAP pCMOS = (PCMOS_MAP)0;
+
+ /* If the realtime clock battery is still functioning, then write */
+ /* the realtime clock values, and return a function value of TRUE. */
+ /* Otherwise, return a function value of FALSE. */
+
+ ucDataByte = DsReadRawClockRegister(RTC_CONTROL_REGISTERD);
+ if (ucDataByte&DS1385_REGD_VALID)
+ {
+ /* Set the realtime clock control to set the time. */
+
+ ucDataByte = DS1385_REGB_HOURS_FMT | DS1385_REGB_SET_TIME;
+ DsWriteRawClockRegister(RTC_CONTROL_REGISTERB, ucDataByte);
+
+ /* Write the realtime clock values. */
+
+ DsWriteClockRegister(RTC_YEAR,
+ (rtems_unsigned8)(pTOD->year%100));
+ if(pTOD->year>=100)
+ {
+ DsWriteClockRegister((rtems_unsigned8)
+ ((unsigned long)&pCMOS->Century),
+ pTOD->year/100);
+ }
+ DsWriteClockRegister(RTC_MONTH,
+ (rtems_unsigned8)pTOD->month);
+ DsWriteClockRegister(RTC_DAY_OF_MONTH,
+ (rtems_unsigned8)pTOD->day);
+ DsWriteClockRegister(RTC_DAY_OF_WEEK,
+ (rtems_unsigned8)
+ (GregorianDay(pTOD) + 1));
+ DsWriteClockRegister(RTC_HOUR,
+ (rtems_unsigned8)pTOD->hour);
+ DsWriteClockRegister(RTC_MINUTE,
+ (rtems_unsigned8)pTOD->minute);
+ DsWriteClockRegister(RTC_SECOND,
+ (rtems_unsigned8)pTOD->second);
+
+ /* Set the realtime clock control to update the time. */
+
+ ucDataByte &= ~DS1385_REGB_SET_TIME;
+ DsWriteRawClockRegister(RTC_CONTROL_REGISTERB, ucDataByte);
+ return;
+
+ }
+ else
+ {
+ return;
+ }
+}
+
+boolean
+timeDsGet (
+ rtems_time_of_day *pTOD
+ )
+
+/*++
+
+Routine Description:
+
+ This routine queries the realtime clock.
+
+Arguments:
+
+ pTOD - Supplies a pointer to a time structure that receives
+ the realtime clock information.
+
+Return Value:
+
+ If the power to the realtime clock has not failed, then the time
+ values are read from the realtime clock and a value of TRUE is
+ returned. Otherwise, a value of FALSE is returned.
+
+--*/
+
+{
+ rtems_unsigned8 ucDataByte;
+ PCMOS_MAP pCMOS = (PCMOS_MAP)0;
+
+ /* If the realtime clock battery is still functioning, then read */
+ /* the realtime clock values, and return a function value of TRUE. */
+ /* Otherwise, return a function value of FALSE. */
+
+ ucDataByte = DsReadRawClockRegister(RTC_CONTROL_REGISTERD);
+ if(ucDataByte&DS1385_REGD_VALID)
+ {
+ /* Wait until the realtime clock is not being updated. */
+
+ do
+ {
+ ucDataByte=DsReadRawClockRegister(RTC_CONTROL_REGISTERA);
+ } while (ucDataByte&DS1385_REGA_UIP);
+
+ /* Read the realtime clock values. */
+
+ pTOD->year=(rtems_unsigned16)
+ (DsReadClockRegister(
+ (rtems_unsigned8)
+ (unsigned long)&pCMOS->Century)
+ *100 + DsReadClockRegister(RTC_YEAR));
+ pTOD->month=DsReadClockRegister(RTC_MONTH);
+ pTOD->day=DsReadClockRegister(RTC_DAY_OF_MONTH);
+ pTOD->hour=DsReadClockRegister(RTC_HOUR);
+ pTOD->minute=DsReadClockRegister(RTC_MINUTE);
+ pTOD->second=DsReadClockRegister(RTC_SECOND);
+ return TRUE;
+ }
+ else
+ {
+ return FALSE;
+ }
+}
+
+void
+timeMkSet (
+ rtems_time_of_day *pTOD
+ )
+
+/*++
+
+Routine Description:
+
+ This routine sets the realtime clock.
+
+ N.B. This routine assumes that the caller has provided any required
+ synchronization to set the realtime clock information.
+
+Arguments:
+
+ pTOD - Supplies a pointer to a time structure that specifies the
+ realtime clock information.
+
+Return Value:
+
+ If the power to the realtime clock has not failed, then the time
+ values are written to the realtime clock and a value of TRUE is
+ returned. Otherwise, a value of FALSE is returned.
+
+--*/
+
+{
+ PMK48T18_NVRAM_MAP pNvRAM = MK48T18_BASE;
+
+ /*
+ * Set the RTC into write mode
+ */
+ pNvRAM->CMOS.Control|=MK48T18_CTRL_WRITE;
+ EIEIO;
+
+ /*
+ * Write the realtime clock values.
+ */
+
+ pNvRAM->CMOS.Year = (rtems_unsigned8)Bin2BCD(pTOD->year%100);
+ if(pTOD->year>=100)
+ {
+ pNvRAM->CMOS.Century=(rtems_unsigned8)
+ Bin2BCD(pTOD->year/100);
+ }
+ pNvRAM->CMOS.Month = (rtems_unsigned8)Bin2BCD(pTOD->month);
+ pNvRAM->CMOS.Date = (rtems_unsigned8)Bin2BCD(pTOD->day);
+ pNvRAM->CMOS.Day = (rtems_unsigned8)(GregorianDay(pTOD) + 1);
+ pNvRAM->CMOS.Hour = (rtems_unsigned8)Bin2BCD(pTOD->hour);
+ pNvRAM->CMOS.Minute = (rtems_unsigned8)Bin2BCD(pTOD->minute);
+ pNvRAM->CMOS.Second = (rtems_unsigned8)Bin2BCD(pTOD->second);
+
+ /*
+ * Set the realtime clock control to update the time.
+ */
+
+ EIEIO;
+ pNvRAM->CMOS.Control&=~MK48T18_CTRL_WRITE;
+}
+
+boolean
+timeMkGet (
+ rtems_time_of_day *pTOD
+ )
+
+/*++
+
+Routine Description:
+
+ This routine queries the realtime clock.
+
+ N.B. This routine is required to provide any synchronization necessary
+ to query the realtime clock information.
+
+Arguments:
+
+ pTOD - Supplies a pointer to a time structure that receives
+ the realtime clock information.
+
+Return Value:
+
+ If the power to the realtime clock has not failed, then the time
+ values are read from the realtime clock and a value of TRUE is
+ returned. Otherwise, a value of FALSE is returned.
+
+--*/
+
+{
+ PMK48T18_NVRAM_MAP pNvRAM = MK48T18_BASE;
+
+ /*
+ * Set the RTC into read mode
+ */
+ pNvRAM->CMOS.Control|=MK48T18_CTRL_READ;
+ EIEIO;
+
+ /*
+ * Read the realtime clock values.
+ */
+
+ pTOD->year = (rtems_unsigned16)(100*BCD2Bin(pNvRAM->CMOS.Century)+
+ BCD2Bin(pNvRAM->CMOS.Year));
+ pTOD->month = (rtems_unsigned8)BCD2Bin(pNvRAM->CMOS.Month);
+ pTOD->day = (rtems_unsigned8)BCD2Bin(pNvRAM->CMOS.Date);
+ pTOD->hour = (rtems_unsigned8)BCD2Bin(pNvRAM->CMOS.Hour);
+ pTOD->minute = (rtems_unsigned8)BCD2Bin(pNvRAM->CMOS.Minute);
+ pTOD->second = (rtems_unsigned8)BCD2Bin(pNvRAM->CMOS.Second);
+
+ /*
+ * Set the realtime clock control to normal mode.
+ */
+ EIEIO;
+ pNvRAM->CMOS.Control&=~MK48T18_CTRL_READ;
+
+ return TRUE;
+}
+
+/*
+ * Set up entry table
+ */
+void
+InitializeRTC(void)
+{
+ rtems_status_code sc;
+
+ switch(ucSystemType)
+ {
+ case SYS_TYPE_PPC1:
+ {
+ if(ucBoardRevMaj<5)
+ {
+ pTimeFunc=&timeDsTable;
+ break;
+ }
+ /*
+ * For the 005 and later drop through to the PPC1a support
+ */
+ }
+
+ case SYS_TYPE_PPC1a:
+ {
+ pTimeFunc=&timeMkTable;
+ break;
+ }
+
+ default:
+ {
+ pTimeFunc=&timeDsTable;
+ break;
+ }
+ }
+
+ /*
+ * Set up mutex semaphore
+ */
+ sc = rtems_semaphore_create (
+ rtems_build_name ('R', 'T', 'C', 's'),
+ 1,
+ RTEMS_BINARY_SEMAPHORE |
+ RTEMS_INHERIT_PRIORITY |
+ RTEMS_PRIORITY,
+ RTEMS_NO_PRIORITY,
+ &semRTC);
+ if (sc != RTEMS_SUCCESSFUL)
+ {
+ rtems_fatal_error_occurred (sc);
+ }
+}
+
+void setRealTimeToRTEMS()
+{
+ rtems_time_of_day rtc_tod;
+
+ rtems_semaphore_obtain(semRTC, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ (pTimeFunc->GetTime)(&rtc_tod);
+ rtems_semaphore_release(semRTC);
+
+ /*
+ * Millenium fix...
+ *
+ * If year is earlier than MIN_YEAR then assume the clock has wrapped from
+ * 1999 to 1900 so advance by a century
+ */
+ if(rtc_tod.year<MIN_YEAR)
+ {
+ rtc_tod.year+=100;
+ rtems_semaphore_obtain(semRTC, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ (pTimeFunc->SetTime)(&rtc_tod);
+ rtems_semaphore_release(semRTC);
+ }
+
+ rtc_tod.ticks=0;
+
+ rtems_clock_set( &rtc_tod );
+}
+
+void setRealTimeFromRTEMS()
+{
+ rtems_time_of_day rtems_tod;
+
+ rtems_clock_get( RTEMS_CLOCK_GET_TOD, &rtems_tod );
+ rtems_semaphore_obtain(semRTC, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
+ (pTimeFunc->SetTime)(&rtems_tod);
+ rtems_semaphore_release(semRTC);
+}
+
+
+int checkRealTime()
+{
+ return 0;
+}
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/universe/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/universe/Makefile.in
new file mode 100644
index 0000000000..9498744792
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/universe/Makefile.in
@@ -0,0 +1,54 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/universe.rel
+
+# C source names, if any, go here -- minus the .c
+C_PIECES=universe
+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_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/universe/universe.c b/c/src/lib/libbsp/powerpc/ppcn_60x/universe/universe.c
new file mode 100644
index 0000000000..16fb887c44
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/universe/universe.c
@@ -0,0 +1,449 @@
+/*
+ * COPYRIGHT (c) 1998 by Radstone Technology
+ *
+ *
+ * THIS FILE IS PROVIDED TO YOU, THE USER, "AS IS", WITHOUT WARRANTY OF ANY
+ * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK
+ * AS TO THE QUALITY AND PERFORMANCE OF ALL CODE IN THIS FILE IS WITH YOU.
+ *
+ * You are hereby granted permission to use, copy, modify, and distribute
+ * this file, provided that this notice, plus the above copyright notice
+ * and disclaimer, appears in all copies. Radstone Technology will provide
+ * no support for this code.
+ *
+ * COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994, 1997.
+ * 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.
+ *
+ * $ld:
+ */
+
+#include <rtems.h>
+#include <assert.h>
+#include <stdio.h>
+
+#include <bsp.h>
+#include <pci.h>
+
+/********************************************************************
+ ********************************************************************
+ ********* *********
+ ********* Prototypes *********
+ ********* *********
+ ********************************************************************
+ ********************************************************************/
+
+typedef struct {
+ rtems_unsigned32 PCI_ID; /* Offset 0x0000 */
+ rtems_unsigned32 PCI_CSR; /* Offset 0x0004 */
+ rtems_unsigned32 PCI_CLASS; /* Offset 0x0008 */
+ rtems_unsigned32 PCI_MISC0; /* Offset 0x000C */
+ rtems_unsigned32 PCI_BS; /* Offset 0x0010 */
+ rtems_unsigned32 Buf_Offset_0x0014[ 0x0A ]; /* Offset 0x0014 */
+ rtems_unsigned32 PCI_MISC1; /* Offset 0x003C */
+ rtems_unsigned32 Buf_Offset_0x0040[ 0x30 ]; /* Offset 0x0040 */
+ rtems_unsigned32 LSI0_CTL; /* Offset 0x0100 */
+ rtems_unsigned32 LSI0_BS; /* Offset 0x0104 */
+ rtems_unsigned32 LSI0_BD; /* Offset 0x0108 */
+ rtems_unsigned32 LSI0_TO; /* Offset 0x010C */
+ rtems_unsigned32 Buf_Offset_0x0110; /* Offset 0x0110 */
+ rtems_unsigned32 LSI1_CTL; /* Offset 0x0114 */
+ rtems_unsigned32 LSI1_BS; /* Offset 0x0118 */
+ rtems_unsigned32 LSI1_BD; /* Offset 0x011C */
+ rtems_unsigned32 LSI1_TO; /* Offset 0x0120 */
+ rtems_unsigned32 Buf_Offset_0x0124; /* Offset 0x0124 */
+ rtems_unsigned32 LSI2_CTL; /* Offset 0x0128 */
+ rtems_unsigned32 LSI2_BS; /* Offset 0x012C */
+ rtems_unsigned32 LSI2_BD; /* Offset 0x0130 */
+ rtems_unsigned32 LSI2_TO; /* Offset 0x0134 */
+ rtems_unsigned32 Buf_Offset_0x0138; /* Offset 0x0138 */
+ rtems_unsigned32 LSI3_CTL; /* Offset 0x013C */
+ rtems_unsigned32 LSI3_BS; /* Offset 0x0140 */
+ rtems_unsigned32 LSI3_BD; /* Offset 0x0144 */
+ rtems_unsigned32 LSI3_TO; /* Offset 0x0148 */
+ rtems_unsigned32 Buf_Offset_0x014C[ 0x09 ]; /* Offset 0x014C */
+ rtems_unsigned32 SCYC_CTL; /* Offset 0x0170 */
+ rtems_unsigned32 SCYC_ADDR; /* Offset 0x0174 */
+ rtems_unsigned32 SCYC_EN; /* Offset 0x0178 */
+ rtems_unsigned32 SCYC_CMP; /* Offset 0x017C */
+ rtems_unsigned32 SCYC_SWP; /* Offset 0x0180 */
+ rtems_unsigned32 LMISC; /* Offset 0x0184 */
+ rtems_unsigned32 SLSI; /* Offset 0x0188 */
+ rtems_unsigned32 L_CMDERR; /* Offset 0x018C */
+ rtems_unsigned32 LAERR; /* Offset 0x0190 */
+ rtems_unsigned32 Buf_Offset_0x0194[ 0x1B ]; /* Offset 0x0194 */
+ rtems_unsigned32 DCTL; /* Offset 0x0200 */
+ rtems_unsigned32 DTBC; /* Offset 0x0204 */
+ rtems_unsigned32 DLA; /* Offset 0x0208 */
+ rtems_unsigned32 Buf_Offset_0x020C; /* Offset 0x020C */
+ rtems_unsigned32 DVA; /* Offset 0x0210 */
+ rtems_unsigned32 Buf_Offset_0x0214; /* Offset 0x0214 */
+ rtems_unsigned32 DCPP; /* Offset 0x0218 */
+ rtems_unsigned32 Buf_Offset_0x021C; /* Offset 0x021C */
+ rtems_unsigned32 DGCS; /* Offset 0x0220 */
+ rtems_unsigned32 D_LLUE; /* Offset 0x0224 */
+ rtems_unsigned32 Buf_Offset_0x0228[ 0x36 ]; /* Offset 0x0228 */
+ rtems_unsigned32 LINT_EN; /* Offset 0x0300 */
+ rtems_unsigned32 LINT_STAT; /* Offset 0x0304 */
+ rtems_unsigned32 LINT_MAP0; /* Offset 0x0308 */
+ rtems_unsigned32 LINT_MAP1; /* Offset 0x030C */
+ rtems_unsigned32 VINT_EN; /* Offset 0x0310 */
+ rtems_unsigned32 VINT_STAT; /* Offset 0x0314 */
+ rtems_unsigned32 VINT_MAP0; /* Offset 0x0318 */
+ rtems_unsigned32 VINT_MAP1; /* Offset 0x031C */
+ rtems_unsigned32 STATID; /* Offset 0x0320 */
+ rtems_unsigned32 V1_STATID; /* Offset 0x0324 */
+ rtems_unsigned32 V2_STATID; /* Offset 0x0328 */
+ rtems_unsigned32 V3_STATID; /* Offset 0x032C */
+ rtems_unsigned32 V4_STATID; /* Offset 0x0330 */
+ rtems_unsigned32 V5_STATID; /* Offset 0x0334 */
+ rtems_unsigned32 V6_STATID; /* Offset 0x0338 */
+ rtems_unsigned32 V7_STATID; /* Offset 0x033C */
+ rtems_unsigned32 Buf_Offset_0x0340[ 0x30 ]; /* Offset 0x0340 */
+ rtems_unsigned32 MAST_CTL; /* Offset 0x0400 */
+ rtems_unsigned32 MISC_CTL; /* Offset 0x0404 */
+ rtems_unsigned32 MISC_STAT; /* Offset 0x0408 */
+ rtems_unsigned32 USER_AM; /* Offset 0x040C */
+ rtems_unsigned32 Buf_Offset_0x0410[ 0x2bc ];/* Offset 0x0410 */
+ rtems_unsigned32 VSI0_CTL; /* Offset 0x0F00 */
+ rtems_unsigned32 VSI0_BS; /* Offset 0x0F04 */
+ rtems_unsigned32 VSI0_BD; /* Offset 0x0F08 */
+ rtems_unsigned32 VSI0_TO; /* Offset 0x0F0C */
+ rtems_unsigned32 Buf_Offset_0x0f10; /* Offset 0x0F10 */
+ rtems_unsigned32 VSI1_CTL; /* Offset 0x0F14 */
+ rtems_unsigned32 VSI1_BS; /* Offset 0x0F18 */
+ rtems_unsigned32 VSI1_BD; /* Offset 0x0F1C */
+ rtems_unsigned32 VSI1_TO; /* Offset 0x0F20 */
+ rtems_unsigned32 Buf_Offset_0x0F24; /* Offset 0x0F24 */
+ rtems_unsigned32 VSI2_CTL; /* Offset 0x0F28 */
+ rtems_unsigned32 VSI2_BS; /* Offset 0x0F2C */
+ rtems_unsigned32 VSI2_BD; /* Offset 0x0F30 */
+ rtems_unsigned32 VSI2_TO; /* Offset 0x0F34 */
+ rtems_unsigned32 Buf_Offset_0x0F38; /* Offset 0x0F38 */
+ rtems_unsigned32 VSI3_CTL; /* Offset 0x0F3C */
+ rtems_unsigned32 VSI3_BS; /* Offset 0x0F40 */
+ rtems_unsigned32 VSI3_BD; /* Offset 0x0F44 */
+ rtems_unsigned32 VSI3_TO; /* Offset 0x0F48 */
+ rtems_unsigned32 Buf_Offset_0x0F4C[ 0x9 ]; /* Offset 0x0F4C */
+ rtems_unsigned32 VRAI_CTL; /* Offset 0x0F70 */
+ rtems_unsigned32 VRAI_BS; /* Offset 0x0F74 */
+ rtems_unsigned32 Buf_Offset_0x0F78[ 0x2 ]; /* Offset 0x0F78 */
+ rtems_unsigned32 VCSR_CTL; /* Offset 0x0F80 */
+ rtems_unsigned32 VCSR_TO; /* Offset 0x0F84 */
+ rtems_unsigned32 V_AMERR; /* Offset 0x0F88 */
+ rtems_unsigned32 VAERR; /* Offset 0x0F8C */
+ rtems_unsigned32 Buf_Offset_0x0F90[ 0x19 ]; /* Offset 0x0F90 */
+ rtems_unsigned32 VCSR_CLR; /* Offset 0x0FF4 */
+ rtems_unsigned32 VCSR_SET; /* Offset 0x0FF8 */
+ rtems_unsigned32 VCSR_BS; /* Offset 0x0FFC */
+} Universe_Memory;
+
+volatile Universe_Memory *UNIVERSE;
+
+/*
+ * PCI_bus_write
+ */
+void PCI_bus_write(
+ volatile rtems_unsigned32 * _addr, /* IN */
+ rtems_unsigned32 _data /* IN */
+)
+{
+ outport_32(_addr, _data);
+}
+
+rtems_unsigned32 PCI_bus_read(
+ volatile rtems_unsigned32 * _addr /* IN */
+)
+{
+ rtems_unsigned32 data;
+
+ inport_32(_addr, data);
+ return data;
+}
+
+/********************************************************************
+ ********************************************************************
+ ********* *********
+ ********* *********
+ ********* *********
+ ********************************************************************
+ ********************************************************************/
+
+/*
+ * Initializes the UNIVERSE chip. This routine is called automatically
+ * by the boot code. This routine should be called by user code only if
+ * a complete PPCn_60x VME initialization is required.
+ */
+
+void InitializeUniverse()
+{
+ rtems_unsigned32 pci_id;
+ rtems_unsigned32 universe_temp_value;
+
+ /*
+ * Verify the UNIVERSE CHIP ID
+ */
+ (void)PCIConfigRead32(0,4,0,PCI_CONFIG_VENDOR_LOW, &pci_id);
+
+ /*
+ * compare to known ID
+ */
+ if (pci_id != 0x000010e3 ){
+ DEBUG_puts ("Invalid PPCN_60X_UNIVERSE_CHIP_ID: ");
+ rtems_fatal_error_occurred( 0x603e0bad );
+ }
+
+ (void)PCIConfigRead32(0,4,0,PCI_CONFIG_BAR_0, &universe_temp_value);
+ UNIVERSE = (Universe_Memory *)(universe_temp_value & ~PCI_ADDRESS_IO_SPACE);
+
+ /*
+ * Set the UNIVERSE PCI Configuration Space Control and Status Register to
+ * medium speed device, Target Back to Back Capable, Master Enable, Target
+ * Memory Enable and Target IO Enable
+ */
+ PCIConfigWrite32(0,4,0,PCI_CONFIG_COMMAND, PCI_ENABLE_IO_SPACE |
+ PCI_ENABLE_MEMORY_SPACE |
+ PCI_ENABLE_BUS_MASTER);
+
+ /*
+ * Turn off the sysfail by setting SYSFAIL bit to 1 on the VCSR_CLR register
+ */
+ PCI_bus_write( &UNIVERSE->VCSR_CLR, 0x40000000 );
+
+#if 0
+ /*
+ * Set VMEbus Slave Image 0 Base Address to 0x04000000 on VSI0_BS register.
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_BS, 0x04000000 );
+
+ /*
+ * Set VMEbus Slave Image 0 Bound Address to 0x05000000 on VSI0_BD register.
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_BD, 0x05000000 );
+
+ /*
+ * VMEbus Slave Image 0 Translation Offset to 0x7C000000 on VSI0_TO
+ * register. Map the VME base address 0x4000000 to local memory address 0x0
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_TO, 0x7C000000 );
+
+ /*
+ * Set the VMEbus Slave Image 0 Control register with write posted,
+ * read prefetch and AM code set for program, data, supervisor and user mode
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_CTL, 0xE0F20000 );
+#endif
+
+ /*
+ * Set the VMEbus Master Control register with retry forever, 256 bytes
+ * posted write transfer count, VMEbus request level 3, RWD, PCI 32 bytes
+ * aligned burst size and PCI bus number to be zero
+ */
+ PCI_bus_write( &UNIVERSE->MAST_CTL, 0x01C00000 );
+
+ /*
+ * VMEbus DMA Transfer Control register with 32 bit VMEbus Maximum Data
+ * width, A32 VMEbus Address Space, AM code to be data, none-privilleged,
+ * single and BLT cycles on VME bus and 64-bit PCI Bus Transactions enable
+ PCI_bus_write( &UNIVERSE->DCTL, 0x00820180 );
+ */
+
+ PCI_bus_write( &UNIVERSE->LSI0_CTL, 0x80700040 );
+ PCI_bus_write( &UNIVERSE->LSI0_BS, 0x04000000 );
+ PCI_bus_write( &UNIVERSE->LSI0_BD, 0x05000000 );
+ PCI_bus_write( &UNIVERSE->LSI0_TO, 0x7C000000 );
+
+
+#if 0
+ /*
+ * Set the PCI Slave Image 0 Control register with posted write enable,
+ * 32 bit data width, A32 VMEbus address base, AM code to be data,
+ * none-privilleged, single and BLT cycles on VME bus with PCI
+ * bus memory space.
+ PCI_bus_write( &UNIVERSE->LSI0_CTL, 0xC0820100 );
+ */
+ PCI_bus_write( &UNIVERSE->LSI0_CTL, 0x80700040 );
+
+ /*
+ * Set the PCI Slave Image 0 Base Address to be
+ * 0x0 on LSI0_BS register.
+ */
+ PCI_bus_write( &UNIVERSE->LSI0_BS, 0x00FF0000 );
+
+ /*
+ * Set the PCI Slave Image 0 Bound Address to be
+ * 0xFFFFF000 on VSI0_BD register.
+ */
+ PCI_bus_write( &UNIVERSE->LSI0_BD, 0x00FFF000 );
+
+ /*
+ * Set the PCI Slave Image 0 Translation Offset to be
+ * 0x0 on VSI0_TO register.
+ * Note: If the actual VME address is bigger than 0x40000000, we need
+ * to set the PCI Slave Image 0 Translation Offset = 0x40000000
+ * register.
+ * i.e. if actual VME ADRR = 0x50000000, then we
+ * need to subtract it by 0x40000000 and set
+ * the LSI0_T0 register to be 0x40000000 and then
+ * perform a PCI data access by adding 0xC0000000 to
+ * 0x10000000 -- which is came form the result of
+ * (0x50000000 - 0x40000000).
+ */
+ PCI_bus_write( &UNIVERSE->LSI0_TO, 0x0 );
+#endif
+
+ /*
+ * Remove the Universe from VMEbus BI-Mode (bus-isolation). Once out of
+ * BI-Mode VMEbus accesses can be made.
+ */
+
+ universe_temp_value = PCI_bus_read( &UNIVERSE->MISC_CTL );
+
+ if (universe_temp_value & 0x100000)
+ PCI_bus_write( &UNIVERSE->MISC_CTL,(universe_temp_value | ~0xFF0FFFFF));
+}
+
+/*
+ * Set the slave VME base address to the specified base address.
+ * Note: Lower 12 bits[11:0] will be masked out prior to setting the VMEbus
+ * Slave Image 0 registers.
+ */
+void set_vme_base_address (
+ rtems_unsigned32 base_address
+)
+{
+ volatile rtems_unsigned32 temp;
+
+ /*
+ * Calculate the current size of the Slave VME image 0
+ */
+ temp = ( PCI_bus_read( &UNIVERSE->VSI0_BD) & 0xFFFFF000) -
+ ( PCI_bus_read( &UNIVERSE->VSI0_BS) & 0xFFFFF000);
+
+ /*
+ * Set the VMEbus Slave Image 0 Base Address to be
+ * the specifed base address on VSI0_BS register.
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_BS, (base_address & 0xFFFFF000) );
+
+ /*
+ * Update the VMEbus Slave Image 0 Bound Address.
+ */
+ PCI_bus_write( &UNIVERSE->VSI0_BD, temp );
+
+ /*
+ * Update the VMEbus Slave Image 0 Translation Offset
+ */
+ temp = 0xFFFFFFFF - (base_address & 0xFFFFF000) + 1 + 0x80000000;
+ PCI_bus_write( &UNIVERSE->VSI0_TO, temp );
+}
+
+/*
+ * Gets the VME base address
+ */
+rtems_unsigned32 get_vme_base_address ()
+{
+ volatile rtems_unsigned32 temp;
+
+ temp = PCI_bus_read( &UNIVERSE->VSI0_BS );
+ temp &= 0xFFFFF000;
+ return (temp);
+}
+
+rtems_unsigned32 get_vme_slave_size()
+{
+ volatile rtems_unsigned32 temp;
+ temp = PCI_bus_read( &UNIVERSE->VSI0_BD);
+ temp &= 0xFFFFF000;
+ temp = temp - get_vme_base_address ();
+ return temp;
+}
+
+/*
+ * Set the size of the VME slave image
+ * Note: The maximum size is up to 24 M bytes. (00000000 - 017FFFFF)
+ */
+void set_vme_slave_size (rtems_unsigned32 size)
+{
+ volatile rtems_unsigned32 temp;
+
+ if (size<0)
+ size = 0;
+
+ if (size > 0x17FFFFF)
+ size = 0x17FFFFF;
+
+ /*
+ * Read the VME slave image base address
+ */
+ temp = get_vme_base_address ();
+
+ /*
+ * Update the VMEbus Slave Image 0 Bound Address.
+ */
+ temp = temp + (size & 0xFFFFF000);
+ PCI_bus_write( &UNIVERSE->VSI0_BD, temp );
+}
+
+#if 0
+/* XXXXX */
+/*
+ * Returns the 16 bit location specified by vme_ptr, which must be a
+ * pointer to VME D16 space
+ */
+rtems_unsigned16 get_vme(
+ rtems_unsigned16 *vme_ptr
+)
+{
+ rtems_unsigned16 result;
+
+ if (vme_ptr > (rtems_unsigned16 *)0x3EFFFFFF)
+ {
+ /*
+ * LSI0_TO register to 0x3EFFF000 if it had not been updated already
+ */
+ if (( PCI_bus_read( &UNIVERSE->LSI0_TO ) & 0xFFFFF000) != 0x3EFFF000)
+ PCI_bus_write( &UNIVERSE->LSI0_TO, 0x3EFFF000 );
+
+ result = (*(rtems_unsigned16 *)(
+ ((rtems_unsigned32)vme_ptr - 0x3EFFF000)+
+ PPCN_60X_PCI_MEM_BASE) );
+ }
+ else
+ result = (*(rtems_unsigned16 *)
+ ((rtems_unsigned32)vme_ptr+PPCN_60X_PCI_MEM_BASE));
+
+ return result;
+}
+
+/*
+ * Stores the 16 bit word at the location specified by vme_ptr, which must
+ * be a pointer to VME D16 space
+ */
+void put_vme(
+ rtems_unsigned16 *vme_ptr,
+ rtems_unsigned16 value
+)
+{
+
+ if (vme_ptr > (rtems_unsigned16 *)0x3EFFFFFF) {
+ /*
+ * LSI0_TO register to 0x3EFFF000 if it had not been updated already
+ */
+ if (( PCI_bus_read( &UNIVERSE->LSI0_TO) & 0xFFFFF000) != 0x3EFFF000)
+ PCI_bus_write( &UNIVERSE->LSI0_TO, 0x3EFFF000 );
+
+ *(rtems_unsigned16 *) (((rtems_unsigned32)vme_ptr - 0x3EFFF000) +
+ PPCN_60X_PCI_MEM_BASE) = value;
+ }
+ else
+ *(rtems_unsigned16 *)((rtems_unsigned32)vme_ptr +
+ PPCN_60X_PCI_MEM_BASE) = value;
+}
+#endif
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/Makefile.in
new file mode 100644
index 0000000000..d17e897c7d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/Makefile.in
@@ -0,0 +1,59 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+PGM=${ARCH}/vectors.rel
+
+# 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=vectors
+S_FILES=$(S_PIECES:%=%.S)
+S_O_FILES=$(S_FILES:%.S=${ARCH}/%.o)
+
+SRCS=$(C_FILES) $(CC_FILES) $(H_FILES) $(S_FILES)
+OBJS=$(C_O_FILES) $(CC_O_FILES) $(S_O_FILES)
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+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 +=
+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
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/README b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/README
new file mode 100644
index 0000000000..4081ae2525
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/README
@@ -0,0 +1,25 @@
+#
+# $Id$
+#
+
+The location of the vectors file object is critical.
+
+From the comments at the head of vectors.s:
+
+ The issue with this file is getting it loaded at the right place.
+ The first vector MUST be at address 0x????0100.
+ How this is achieved is dependant on the tool chain.
+
+ However the basic mechanism for ELF assemblers is to create a
+ section called ".vectors", which will be loaded to an address
+ between 0x????0000 and 0x????0100 (inclusive) via a link script.
+
+ The basic mechanism for XCOFF assemblers is to place it in the
+ normal text section, and arrange for this file to be located
+ at an appropriate position on the linker command line.
+
+ The variable 'PPC_VECTOR_FILE_BASE' must be defined to be the
+ offset from 0x????0000 to the first location in the file. This
+ will usually be 0x0000 or 0x0100.
+
+Andrew Bray 18/8/1995
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/align_h.S b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/align_h.S
new file mode 100644
index 0000000000..d16298343d
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/align_h.S
@@ -0,0 +1,434 @@
+/* align_h.s 1.1 - 95/12/04
+ *
+ * This file contains the assembly code for the PowerPC 403
+ * alignment exception handler for RTEMS.
+ *
+ * Based upon IBM provided code with the following release:
+ *
+ * This source code has been made available to you by IBM on an AS-IS
+ * basis. Anyone receiving this source is licensed under IBM
+ * copyrights to use it in any way he or she deems fit, including
+ * copying it, modifying it, compiling it, and redistributing it either
+ * with or without modifications. No license under IBM patents or
+ * patent applications is to be implied by the copyright license.
+ *
+ * Any user of this software should understand that IBM cannot provide
+ * technical support for this software and will not be responsible for
+ * any consequences resulting from the use of this software.
+ *
+ * Any person who transfers this source code or any derivative work
+ * must include the IBM copyright notice, this paragraph, and the
+ * preceding two paragraphs in the transferred software.
+ *
+ * COPYRIGHT I B M CORPORATION 1995
+ * LICENSED MATERIAL - PROGRAM PROPERTY OF I B M
+ *
+ * Modifications:
+ *
+ * Author: Andrew Bray <andy@i-cubed.co.uk>
+ *
+ * COPYRIGHT (c) 1995 by i-cubed ltd.
+ *
+ * To anyone who acknowledges that this file is provided "AS IS"
+ * without any express or implied warranty:
+ * permission to use, copy, modify, and distribute this file
+ * for any purpose is hereby granted without fee, provided that
+ * the above copyright notice and this notice appears in all
+ * copies, and that the name of i-cubed limited not be used in
+ * advertising or publicity pertaining to distribution of the
+ * software without specific, written prior permission.
+ * i-cubed limited makes no representations about the suitability
+ * of this software for any purpose.
+ *
+ * $Id$
+ */
+
+#include "asm.h"
+#include "bsp.h"
+
+.set CACHE_SIZE,16 # cache line size of 32 bytes
+.set CACHE_SIZE_L2,4 # cache line size, log 2
+
+.set Open_gpr0,0
+.set Open_gpr1,4
+.set Open_gpr2,8
+.set Open_gpr3,12
+.set Open_gpr4,16
+.set Open_gpr5,20
+.set Open_gpr6,24
+.set Open_gpr7,28
+.set Open_gpr8,32
+.set Open_gpr9,36
+.set Open_gpr10,40
+.set Open_gpr11,44
+.set Open_gpr12,48
+.set Open_gpr13,52
+.set Open_gpr14,56
+.set Open_gpr15,60
+.set Open_gpr16,64
+.set Open_gpr17,68
+.set Open_gpr18,72
+.set Open_gpr19,76
+.set Open_gpr20,80
+.set Open_gpr21,84
+.set Open_gpr22,88
+.set Open_gpr23,92
+.set Open_gpr24,96
+.set Open_gpr25,100
+.set Open_gpr26,104
+.set Open_gpr27,108
+.set Open_gpr28,112
+.set Open_gpr29,116
+.set Open_gpr30,120
+.set Open_gpr31,124
+.set Open_xer,128
+.set Open_lr,132
+.set Open_ctr,136
+.set Open_cr,140
+.set Open_srr2,144
+.set Open_srr3,148
+.set Open_srr0,152
+.set Open_srr1,156
+
+
+/*
+ * This code makes several assumptions for processing efficiency
+ * * General purpose registers are continuous in the image, beginning with
+ * Open_gpr0
+ * * Hash table is highly dependent on opcodes - opcode changes *will*
+ * require rework of the instruction decode mechanism.
+ */
+
+ .text
+ .globl align_h
+
+ .align CACHE_SIZE_L2
+align_h:
+ /*-----------------------------------------------------------------------
+ * Store GPRs in Open Reg save area
+ * Set up r2 as base reg, r1 pointing to Open Reg save area
+ *----------------------------------------------------------------------*/
+ stmw r0,ALIGN_REGS(r0)
+ li r1,ALIGN_REGS
+ /*-----------------------------------------------------------------------
+ * Store special purpose registers in reg save area
+ *----------------------------------------------------------------------*/
+ mfxer r7
+ mflr r8
+ mfcr r9
+ mfctr r10
+ stw r7,Open_xer(r1)
+ stw r8,Open_lr(r1)
+ stw r9,Open_cr(r1)
+ stw r10,Open_ctr(r1)
+ mfspr r7, srr2 /* SRR 2 */
+ mfspr r8, srr3 /* SRR 3 */
+ mfspr r9, srr0 /* SRR 0 */
+ mfspr r10, srr1 /* SRR 1 */
+ stw r7,Open_srr2(r1)
+ stw r8,Open_srr3(r1)
+ stw r9,Open_srr0(r1)
+ stw r10,Open_srr1(r1)
+
+/* Set up common registers */
+ mfspr r5, dear /* DEAR: R5 is data exception address */
+ lwz r9,Open_srr0(r1) /* get faulting instruction */
+ addi r7,r9,4 /* bump instruction */
+ stw r7,Open_srr0(r1) /* restore to image */
+ lwz r9, 0(r9) /* retrieve actual instruction */
+ rlwinm r6,r9,18,25,29 /* r6 is RA * 4 field from instruction */
+ rlwinm r7,r9,6,26,31 /* r7 is primary opcode */
+ bl ref_point /* establish addressibility */
+ref_point:
+ mflr r11 /* r11 is the anchor point for ref_point */
+ addi r10, r7, -31 /* r10 = r7 - 31 */
+ rlwinm r10,r10,2,2,31 /* r10 *= 4 */
+ add r10, r10, r11 /* r10 += anchor point */
+ lwz r10, primary_jt-ref_point(r10)
+ mtlr r10
+ rlwinm r8,r9,13,25,29 /* r8 is RD * 4 */
+ la r7,Open_gpr0(r1) /* r7 is address of GPR 0 in list */
+ blr
+primary_jt:
+ .long xform
+ .long lwz
+ .long lwzu
+ .long 0
+ .long 0
+ .long stw
+ .long stwu
+ .long 0
+ .long 0
+ .long lhz
+ .long lhzu
+ .long lha
+ .long lhau
+ .long sth
+ .long sthu
+ .long lmw
+ .long stmw
+/*
+ * handlers
+ */
+/*
+ * xform instructions require an additional decode. Fortunately, a relatively
+ * simple hash step breaks the instructions out with no collisions
+ */
+xform:
+ rlwinm r7,r9,31,22,31 /* r7 is secondary opcode */
+ rlwinm r10,r7,27,5,31 /* r10 = r7 >> 5 */
+ add r10,r7,r10 /* r10 = r7 + r10 */
+ rlwinm r10,r10,2,25,29 /* r10 = (r10 & 0x1F) * 4 */
+ add r10,r10,r11 /* r10 += anchor point */
+ lwz r10, secondary_ht-ref_point(r10)
+ mtlr r10
+ la r7,Open_gpr0(r1) /* r7 is address of GPR 0 in list */
+ rlwinm r8,r9,13,25,29 /* r8 is RD * 4 */
+ blrl
+
+secondary_ht:
+ .long lhzux /* b 0 0x137 */
+ .long lhax /* b 1 0x157 */
+ .long lhaux /* b 2 0x177 */
+ .long sthx /* b 3 0x197 */
+ .long sthux /* b 4 0x1b7 */
+ .long 0 /* b 5 */
+ .long lwbrx /* b 6 0x216 */
+ .long 0 /* b 7 */
+ .long 0 /* b 8 */
+ .long 0 /* b 9 */
+ .long stwbrx /* b A 0x296 */
+ .long 0 /* b B */
+ .long 0 /* b C */
+ .long 0 /* b D */
+ .long lhbrx /* b E 0x316 */
+ .long 0 /* b F */
+ .long 0 /* b 10 */
+ .long 0 /* b 11 */
+ .long sthbrx /* b 12 0x396 */
+ .long 0 /* b 13 */
+ .long lwarx /* b 14 0x014 */
+ .long dcbz /* b 15 0x3f6 */
+ .long 0 /* b 16 */
+ .long lwzx /* b 17 0x017 */
+ .long lwzux /* b 18 0x037 */
+ .long 0 /* b 19 */
+ .long stwcx /* b 1A 0x096 */
+ .long stwx /* b 1B 0x097 */
+ .long stwux /* b 1C 0x0B7 */
+ .long 0 /* b 1D */
+ .long 0 /* b 1E */
+ .long lhzx /* b 1F 0x117 */
+
+/*
+ * for all handlers
+ * r4 - Addressability to interrupt context
+ * r5 - DEAR address (faulting data address)
+ * r6 - RA field * 4
+ * r7 - Address of GPR 0 in image
+ * r8 - RD field * 4
+ * r9 - Failing instruction
+ */
+
+/* Load halfword algebraic with update */
+lhau:
+/* Load halfword algebraic with update indexed */
+lhaux:
+ stwx r5,r7,r6 /* update RA with effective addr */
+
+/* Load halfword algebraic */
+lha:
+/* Load halfword algebraic indexed */
+lhax:
+ lswi r10,r5,2 /* load two bytes into r10 */
+ srawi r10,r10,16 /* shift right 2 bytes, extending sign */
+ stwx r10,r7,r8 /* update reg image */
+ b align_complete /* return */
+
+/* Load Half Word Byte-Reversed Indexed */
+lhbrx:
+ lswi r10,r5,2 /* load two bytes from DEAR into r10 */
+ rlwinm r10,r10,0,0,15 /* mask off lower 2 bytes */
+ stwbrx r10,r7,r8 /* store reversed in reg image */
+ b align_complete /* return */
+
+/* Load Half Word and Zero with Update */
+lhzu:
+/* Load Half Word and Zero with Update Indexed */
+lhzux:
+ stwx r5,r7,r6 /* update RA with effective addr */
+
+/* Load Half Word and Zero */
+lhz:
+/* Load Half Word and Zero Indexed */
+lhzx:
+ lswi r10,r5,2 /* load two bytes from DEAR into r10 */
+ rlwinm r10,r10,16,16,31 /* shift right 2 bytes, with zero fill */
+ stwx r10,r7,r8 /* update reg image */
+ b align_complete /* return */
+
+/*
+ * Load Multiple Word
+ */
+lmw:
+ lwzx r9,r6,r7 /* R9 contains saved value of RA */
+ addi r10,r7,32*4 /* r10 points to r31 in image + 4 */
+ rlwinm r8,r8,30,2,31 /* r8 >>= 2 (recovers RT) */
+ subfic r8,r8,32 /* r8 is reg count to load */
+ mtctr r8 /* load counter */
+ addi r8,r8,-1 /* r8-- */
+ rlwinm r8,r8,2,2,31 /* r8 *= 4 */
+ add r5,r5,r8 /* update DEAR to point to last reg */
+lwmloop:
+ lswi r11,r5,4 /* load r11 with 4 bytes from DEAR */
+ stwu r11,-4(r10) /* load image and decrement pointer */
+ addi r5,r5,-4 /* decrement effective address */
+ bdnz lwmloop
+ stwx r9,r6,r7 /* restore RA (in case it was trashed) */
+ b align_complete /* return */
+
+/*
+ * Load Word and Reserve Indexed
+ */
+lwarx:
+ lswi r10,r5,4 /* load four bytes from DEAR into r10 */
+ stwx r10,r7,r8 /* update reg image */
+ rlwinm r5,r5,0,0,29 /* Word align address */
+ lwarx r10,0,r5 /* Set reservation */
+ b align_complete /* return */
+
+/*
+ * Load Word Byte-Reversed Indexed
+ */
+lwbrx:
+ lswi r10,r5,4 /* load four bytes from DEAR into r10 */
+ stwbrx r10,r7,r8 /* store reversed in reg image */
+ b align_complete /* return */
+
+/* Load Word and Zero with Update */
+lwzu:
+/* Load Word and Zero with Update Indexed */
+lwzux:
+ stwx r5,r7,r6 /* update RA with effective addr */
+
+/* Load Word and Zero */
+lwz:
+/* Load Word and Zero Indexed */
+lwzx:
+ lswi r10,r5,4 /* load four bytes from DEAR into r10 */
+ stwx r10,r7,r8 /* update reg image */
+ b align_complete /* return */
+
+/* Store instructions */
+
+/* */
+/* Store Half Word and Update */
+sthu:
+/* Store Half Word and Update Indexed */
+sthux:
+ stwx r5,r7,r6 /* Update RA with effective address */
+
+/* Store Half Word */
+sth:
+/* Store Half Word Indexed */
+sthx:
+ lwzx r10,r8,r7 /* retrieve source register value */
+ rlwinm r10,r10,16,0,15 /* move two bytes to high end of reg */
+ stswi r10,r5,2 /* store bytes to DEAR address */
+ b align_complete /* return */
+
+/* */
+/* Store Half Word Byte-Reversed Indexed */
+sthbrx:
+ lwbrx r10,r8,r7 /* retrieve src reg value byte reversed */
+ stswi r10,r5,2 /* move two bytes to DEAR address */
+ b align_complete /* return */
+
+/* */
+/* Store Multiple Word */
+stmw:
+ addi r10,r7,32*4 /* r10 points to r31 in image + 4 */
+ rlwinm r8,r8,30,2,31 /* r8 >>= 2 (recovers RT) */
+ subfic r8,r8,32 /* r8 is reg count to load */
+ mtctr r8 /* load counter */
+ addi r8,r8,-1 /* r8-- */
+ rlwinm r8,r8,2,2,31 /* r8 *= 4 */
+ add r5,r5,r8 /* update DEAR to point to last reg */
+stmloop:
+ lwzu r11,-4(r10) /* get register value */
+ stswi r11,r5,4 /* output to DEAR address */
+ addi r5,r5,-4 /* decrement effective address */
+ bdnz stmloop
+ b align_complete /* return */
+
+/* */
+/* Store Word and Update */
+stwu:
+/* Store Word and Update Indexed */
+stwux:
+ stwx r5,r7,r6 /* Update RA with effective address */
+
+/* Store Word */
+stw:
+/* Store Word Indexed */
+stwx:
+ lwzx r10,r8,r7 /* retrieve source register value */
+ stswi r10,r5,4 /* store bytes to DEAR address */
+ b align_complete /* return */
+
+/* */
+/* Store Word Byte-Reversed Indexed */
+stwbrx:
+ lwbrx r10,r8,r7 /* retrieve src reg value byte reversed */
+ stswi r10,r5,4 /* move two bytes to DEAR address */
+ b align_complete /* return */
+
+/* */
+/* Store Word Conditional Indexed */
+stwcx:
+ rlwinm r10,r5,0,0,29 /* r10 = word aligned DEAR */
+ lwz r11,0(r10) /* save original value of store */
+ stwcx. r11,r0,r10 /* attempt store to address */
+ bne stwcx_moveon /* store failed, move on */
+ stw r11,0(r10) /* repair damage */
+ lwzx r9,r7,r8 /* get register value */
+ stswi r10,r5,4 /* store bytes to DEAR address */
+stwcx_moveon:
+ mfcr r11 /* get condition reg */
+ lwz r9,Open_cr(r1) /* get condition reg image */
+ rlwimi r9,r11,0,0,2 /* insert 3 CR bits into cr image */
+ lwz r11,Open_xer(r1) /* get XER reg */
+ rlwimi r9,r11,29,2,2 /* insert XER SO bit into cr image */
+ stw r9,Open_cr(r1) /* store cr image */
+ b align_complete /* return */
+
+/* */
+/* Data Cache Block Zero */
+dcbz:
+ rlwinm r5,r5,0,0,31-CACHE_SIZE_L2
+ /* get address to nearest Cache line */
+ addi r5,r5,-4 /* adjust by a word */
+ addi r10,r0,CACHE_SIZE/4 /* set counter value */
+ mtctr r10
+ addi r11,r0,0 /* r11 = 0 */
+dcbz_loop:
+ stwu r11,4(r5) /* store a word and update EA */
+ bdnz dcbz_loop
+ b align_complete /* return */
+
+align_complete:
+ /*-----------------------------------------------------------------------
+ * Restore regs and return from the interrupt
+ *----------------------------------------------------------------------*/
+ lmw r24,Open_xer+ALIGN_REGS(r0)
+ mtxer r24
+ mtlr r25
+ mtctr r26
+ mtcrf 0xFF, r27
+ mtspr srr2, r28 /* SRR 2 */
+ mtspr srr3, r29 /* SRR 3 */
+ mtspr srr0, r30 /* SRR 0 */
+ mtspr srr1, r31 /* SRR 1 */
+ lmw r1,Open_gpr1+ALIGN_REGS(r0)
+ lwz r0,Open_gpr0+ALIGN_REGS(r0)
+ rfi
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/vectors.S b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/vectors.S
new file mode 100644
index 0000000000..787dbf1eb9
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/vectors/vectors.S
@@ -0,0 +1,297 @@
+/*
+ * (c) 1998, Radstone Technology plc.
+ *
+ *
+ * This is an unpublished work the copyright in which vests
+ * in Radstone Technology plc. All rights reserved.
+ *
+ * The information contained herein is the property of Radstone
+ * Technology plc. and is supplied without liability for
+ * errors or omissions and no part may be reproduced, used or
+ * disclosed except as authorized by contract or other written
+ * permission. The copyright and the foregoing
+ * restriction on reproduction, use and disclosure extend to
+ * all the media in which this information may be
+ * embodied.
+ *
+ */
+/* vectors.s 1.1 - 95/12/04
+ *
+ * This file contains the assembly code for the PowerPC
+ * interrupt veneers for RTEMS.
+ *
+ */
+
+/*
+ * The issue with this file is getting it loaded at the right place.
+ * The first vector MUST be at address 0x????0100.
+ * How this is achieved is dependant on the tool chain.
+ *
+ * However the basic mechanism for ELF assemblers is to create a
+ * section called ".vectors", which will be loaded to an address
+ * between 0x????0000 and 0x????0100 (inclusive) via a link script.
+ *
+ * The basic mechanism for XCOFF assemblers is to place it in the
+ * normal text section, and arrange for this file to be located
+ * at an appropriate position on the linker command line.
+ *
+ * The variable 'PPC_VECTOR_FILE_BASE' must be defined to be the
+ * offset from 0x????0000 to the first location in the file. This
+ * will usually be 0x0000 or 0x0100.
+ *
+ * $Id$
+ */
+
+#include "asm.h"
+#include "bsp.h"
+
+#ifndef PPC_VECTOR_FILE_BASE
+#error "PPC_VECTOR_FILE_BASE is not defined."
+#endif
+
+ .set IP_LINK, 0
+#if (PPC_ABI == PPC_ABI_POWEROPEN || PPC_ABI == PPC_ABI_GCC27)
+ .set IP_0, (IP_LINK + 56)
+#else
+ .set IP_0, (IP_LINK + 8)
+#endif
+ .set IP_2, (IP_0 + 4)
+
+ .set IP_3, (IP_2 + 4)
+ .set IP_4, (IP_3 + 4)
+ .set IP_5, (IP_4 + 4)
+ .set IP_6, (IP_5 + 4)
+
+ .set IP_7, (IP_6 + 4)
+ .set IP_8, (IP_7 + 4)
+ .set IP_9, (IP_8 + 4)
+ .set IP_10, (IP_9 + 4)
+
+ .set IP_11, (IP_10 + 4)
+ .set IP_12, (IP_11 + 4)
+ .set IP_13, (IP_12 + 4)
+ .set IP_28, (IP_13 + 4)
+
+ .set IP_29, (IP_28 + 4)
+ .set IP_30, (IP_29 + 4)
+ .set IP_31, (IP_30 + 4)
+ .set IP_CR, (IP_31 + 4)
+
+ .set IP_CTR, (IP_CR + 4)
+ .set IP_XER, (IP_CTR + 4)
+ .set IP_LR, (IP_XER + 4)
+ .set IP_PC, (IP_LR + 4)
+
+ .set IP_MSR, (IP_PC + 4)
+
+ .set IP_END, (IP_MSR + 16)
+
+ /* Where this file will be loaded */
+ .set file_base, PPC_VECTOR_FILE_BASE
+
+ /* Vector offsets */
+ .set reset_vector,0x0100
+ .set mach_vector,0x0200
+ .set prot_vector,0x0300
+ .set isi_vector,0x0400
+ .set ext_vector,0x0500
+ .set align_vector,0x0600
+ .set prog_vector,0x0700
+ .set float_vector,0x0800
+ .set dec_vector,0x0900
+ .set sys_vector,0x00C00
+ .set trace_vector, 0x0d00
+ .set itm_vector,0x01000
+ .set dltm_vector,0x1100
+ .set dstm_vector,0x1200
+ .set addr_vector,0x1300
+ .set sysmgmt_vector,0x1400
+
+/* Go to the right section */
+#if PPC_ASM == PPC_ASM_ELF
+ .section .vectors,"awx",@progbits
+#elif PPC_ASM == PPC_ASM_XCOFF
+ .csect .text[PR]
+#endif
+
+ PUBLIC_VAR (__vectors)
+SYM (__vectors):
+
+#if PPCN_60X_USE_DINK
+ .org reset_vector - file_base
+ /* This is where the DINK soft reset handler is located */
+ ba 0xfff00180
+
+ .org mach_vector - file_base
+ ba 0xfff00200
+
+ .org prot_vector - file_base
+ ba 0xfff00300
+
+ .org isi_vector - file_base
+ ba 0xfff00400
+
+ .org ext_vector - file_base
+ rfi
+
+ .org align_vector - file_base
+ ba 0xfff00600
+
+ .org prog_vector - file_base
+ ba 0xfff00700
+
+ .org float_vector - file_base
+ ba 0xfff00800
+
+ .org dec_vector - file_base
+ rfi
+
+ .org sys_vector - file_base
+ ba 0xfff00C00
+
+ .org trace_vector - file_base
+ ba 0xfff00d00
+
+ .org itm_vector - file_base
+ ba 0xfff01000
+
+ .org dltm_vector - file_base
+ ba 0xfff01100
+
+ .org dstm_vector - file_base
+ ba 0xfff01200
+
+ .org addr_vector - file_base
+ ba 0xfff01300
+
+ .org sysmgmt_vector - file_base
+ ba 0xfff01400
+#else
+ .org reset_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,1
+display_exc:
+ stw r3,IP_3(r1)
+ stw r5,IP_5(r1)
+ /*
+ * Enable data and instruction address translation
+ */
+ li r3,MSR_IR | MSR_DR
+ mtmsr r3
+ lis r3,0x8000
+ stb r4,0x860(r3)
+ addi r4,r4,0x30
+waitfortx:
+ lbz r5,0x3fd(r3)
+ andi. r5,r5,0x20
+ beq waitfortx
+ stb r4,0x3f8(r3)
+ li r5,0
+ stw r4,0x00(r5)
+ mfsrr0 r4
+ stw r4,0x04(r5)
+ mfsrr1 r4
+ stw r4,0x08(r5)
+ lwz r4,IP_4(r1)
+ lwz r5,IP_5(r1)
+ lwz r3,IP_3(r1)
+ addi r1,r1,IP_END
+ rfi
+
+ .org mach_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ stw r3,IP_3(r1)
+ lis r4,0
+ mfspr r3,srr0
+ stw r3,0x00(r4)
+ mfspr r3,srr1
+ stw r3,0x04(r4)
+ stw r5,0x08(r4)
+ stw r2,0x0c(r4)
+ stw r11,0x10(r4)
+ stw r12,0x14(r4)
+ dcbst 0,r4
+ li r4,0x02
+ b display_exc
+
+ .org prot_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x03
+ b display_exc
+
+ .org isi_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x04
+ b display_exc
+
+ .org ext_vector - file_base
+ rfi
+
+ .org align_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x06
+ b display_exc
+
+ .org prog_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x07
+ b display_exc
+
+ .org float_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x08
+ b display_exc
+
+ .org dec_vector - file_base
+ rfi
+
+ .org sys_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0a
+ b display_exc
+
+ .org trace_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0b
+ b display_exc
+
+ .org itm_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0c
+ b display_exc
+
+ .org dltm_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0d
+ b display_exc
+
+ .org dstm_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0e
+ b display_exc
+
+ .org addr_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x0f
+ b display_exc
+
+ .org sysmgmt_vector - file_base
+ stwu r1, -(IP_END)(r1)
+ stw r4,IP_4(r1)
+ li r4,0x00
+ b display_exc
+#endif
+
diff --git a/c/src/lib/libbsp/powerpc/ppcn_60x/wrapup/Makefile.in b/c/src/lib/libbsp/powerpc/ppcn_60x/wrapup/Makefile.in
new file mode 100644
index 0000000000..d6b2ed0bad
--- /dev/null
+++ b/c/src/lib/libbsp/powerpc/ppcn_60x/wrapup/Makefile.in
@@ -0,0 +1,59 @@
+#
+# $Id$
+#
+
+@SET_MAKE@
+srcdir = @srcdir@
+VPATH = @srcdir@
+RTEMS_ROOT = @top_srcdir@
+PROJECT_ROOT = @PROJECT_ROOT@
+
+# We only build the network device driver if HAS_NETWORK was defined
+NETWORK_DRIVER_yes_V = network
+NETWORK_DRIVER = $(NETWORK_DRIVER_$(HAS_NETWORK)_V)
+
+BSP_PIECES=startup clock console timer tod \
+ $(NETWORK_DRIVER) nvram universe pci vectors
+# pieces to pick up out of libcpu/$(RTEMS_CPU)
+CPU_PIECES=
+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, $(CPU_PIECES), \
+ ../../../../libcpu/$(RTEMS_CPU)/$(piece)/$(ARCH)/$(piece).rel) \
+ $(foreach piece, $(GENERIC_PIECES), \
+ ../../../$(piece)/$(ARCH)/$(piece).rel)
+LIB=$(ARCH)/libbsp.a
+
+include $(RTEMS_ROOT)/make/custom/$(RTEMS_BSP).cfg
+include $(RTEMS_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
+