changeset 1223:dbcfe4e0dbd2

New platform - TAMS MOAB - and generic changes to support it
author gthomas
date Fri, 19 Sep 2003 17:11:18 +0000
parents f0bd64ec9405
children 60ed8b1b4c32
files packages/ChangeLog packages/NEWS packages/devs/eth/powerpc/moab/current/ChangeLog packages/devs/eth/powerpc/moab/current/cdl/moab_eth_drivers.cdl packages/devs/eth/powerpc/moab/current/include/moab_eth.inl packages/devs/eth/powerpc/ppc405/current/ChangeLog packages/devs/eth/powerpc/ppc405/current/cdl/ppc405_eth_drivers.cdl packages/devs/eth/powerpc/ppc405/current/src/if_ppc405.c packages/devs/eth/powerpc/ppc405/current/src/ppc405_enet.h packages/devs/flash/atmel/at49xxxx/current/ChangeLog packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx.inl packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx_parts.inl packages/devs/flash/powerpc/moab/current/cdl/flash_moab.cdl packages/devs/flash/powerpc/moab/current/src/moab_flash.c packages/devs/flash/powerpc/moab/current/src/moab_nand_flash.c packages/devs/flash/toshiba/tc58xxx/current/ChangeLog packages/devs/flash/toshiba/tc58xxx/current/cdl/flash_toshiba_tc58xxx.cdl packages/devs/flash/toshiba/tc58xxx/current/include/flash_tc58xxx.inl packages/devs/flash/toshiba/tc58xxx/current/include/flash_tc58xxx_parts.inl packages/devs/serial/generic/16x5x/current/ChangeLog packages/devs/serial/generic/16x5x/current/src/ser_16x5x.c packages/devs/serial/powerpc/ppc405/current/ChangeLog packages/devs/serial/powerpc/ppc405/current/cdl/ser_powerpc_ppc405.cdl packages/devs/serial/powerpc/ppc405/current/include/powerpc_ppc405_ser.inl packages/devs/wallclock/dallas/ds1307/current/ChangeLog packages/devs/wallclock/dallas/ds1307/current/cdl/wallclock_ds1307.cdl packages/devs/wallclock/dallas/ds1307/current/src/ds1307.cxx packages/devs/wallclock/powerpc/moab/current/ChangeLog packages/devs/wallclock/powerpc/moab/current/cdl/moab_wallclock_drivers.cdl packages/devs/wallclock/powerpc/moab/current/include/devices_wallclock_moab.inl packages/ecos.db packages/hal/powerpc/arch/current/ChangeLog packages/hal/powerpc/arch/current/cdl/hal_powerpc.cdl packages/hal/powerpc/arch/current/include/hal_io.h packages/hal/powerpc/arch/current/src/hal_mk_defs.c packages/hal/powerpc/arch/current/src/vectors.S packages/hal/powerpc/moab/current/ChangeLog packages/hal/powerpc/moab/current/cdl/hal_powerpc_moab.cdl packages/hal/powerpc/moab/current/include/hal_diag.h packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.h packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.ldi packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.mlt packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.h packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.ldi packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.mlt packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.h packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.ldi packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.mlt packages/hal/powerpc/moab/current/include/plf.inc packages/hal/powerpc/moab/current/include/plf_cache.h packages/hal/powerpc/moab/current/include/plf_intr.h packages/hal/powerpc/moab/current/include/plf_io.h packages/hal/powerpc/moab/current/include/plf_regs.h packages/hal/powerpc/moab/current/include/plf_stub.h packages/hal/powerpc/moab/current/misc/redboot_BOOT.ecm packages/hal/powerpc/moab/current/misc/redboot_RAM+FLASH.ecm packages/hal/powerpc/moab/current/misc/redboot_RAM.ecm packages/hal/powerpc/moab/current/misc/redboot_ROM.ecm packages/hal/powerpc/moab/current/misc/redboot_ROMRAM.ecm packages/hal/powerpc/moab/current/sa_tests/Makefile packages/hal/powerpc/moab/current/sa_tests/flash_test.c packages/hal/powerpc/moab/current/sa_tests/ppc.inc packages/hal/powerpc/moab/current/sa_tests/ppc_dram.ld packages/hal/powerpc/moab/current/sa_tests/ppc_ocm.ld packages/hal/powerpc/moab/current/sa_tests/sdram_test.c packages/hal/powerpc/moab/current/sa_tests/start.S packages/hal/powerpc/moab/current/sa_tests/tty.c packages/hal/powerpc/moab/current/src/hal_aux.c packages/hal/powerpc/moab/current/src/moab.S packages/hal/powerpc/moab/current/src/plf_redboot_linux_exec.c packages/hal/powerpc/moab/current/support/make_MOAB_flash.c packages/hal/powerpc/ppc40x/current/ChangeLog packages/hal/powerpc/ppc40x/current/cdl/hal_powerpc_ppc40x.cdl packages/hal/powerpc/ppc40x/current/include/var_cache.h packages/hal/powerpc/ppc40x/current/include/var_intr.h packages/hal/powerpc/ppc40x/current/include/var_io.h packages/hal/powerpc/ppc40x/current/include/var_regs.h packages/hal/powerpc/ppc40x/current/include/variant.inc packages/hal/powerpc/ppc40x/current/src/hal_diag.c packages/hal/powerpc/ppc40x/current/src/ppc405_pci.c packages/hal/powerpc/ppc40x/current/src/var_intr.c packages/hal/powerpc/ppc40x/current/src/var_misc.c packages/io/flash/current/ChangeLog packages/io/flash/current/cdl/io_flash.cdl packages/io/flash/current/include/flash.h packages/io/flash/current/src/flash.c packages/io/wallclock/current/ChangeLog packages/io/wallclock/current/tests/wallclock.cxx packages/redboot/current/ChangeLog packages/redboot/current/cdl/redboot.cdl packages/redboot/current/include/flash_config.h packages/redboot/current/include/redboot.h packages/redboot/current/src/alias.c packages/redboot/current/src/fconfig.c packages/redboot/current/src/flash.c packages/redboot/current/src/load.c packages/redboot/current/src/main.c packages/redboot/current/src/net/net_io.c packages/redboot/current/src/net/tftp_client.c packages/redboot/current/src/time_date.cxx
diffstat 100 files changed, 10573 insertions(+), 1216 deletions(-) [+]
line wrap: on
line diff
--- a/packages/ChangeLog
+++ b/packages/ChangeLog
@@ -1,3 +1,10 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* ecos.db: 
+	New platform - TAMS MOAB (PowerPC 405GPr)
+	New NAND FLASH drivers - Toshiba 58CXXX
+	New RTC driver - Dallas DS1307
+
 2003-08-22  Chris Garry  <cgarry@sweeneydesign.co.uk>
 
 	* ecos.db: Add new VNC server package.
--- a/packages/NEWS
+++ b/packages/NEWS
@@ -1,3 +1,6 @@
+* New port to TAMS MOAB (PowerPC 405GPr) development board
+* FLASH layer can now support NAND devices
+* RedBoot 'fconfig' data can now be stored in either FLASH or EEPROM
 * VNC server (remote access graphic system), contributed by
   Chris Garry  <cgarry@sweeneydesign.co.uk>
 * New port to Analogue & Micro Rattler (Motorola MPC8250)
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/moab/current/ChangeLog
@@ -0,0 +1,43 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/moab_eth.inl: 
+	* cdl/moab_eth_drivers.cdl: New package - ethernet support for
+	TAMS MOAB (PowerPC 405GPr) board
+
+//===========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//===========================================================================
+	
+	
+
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/moab/current/cdl/moab_eth_drivers.cdl
@@ -0,0 +1,94 @@
+#====================================================================
+#
+#      moab_eth_drivers.cdl
+#
+#      Hardware specifics for TAMS MOAB ethernet
+#
+#====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      gthomas
+# Original data:  gthomas
+# Contributors:   gthomas
+# Date:           2003-08-19
+#
+#####DESCRIPTIONEND####
+#
+#====================================================================
+
+cdl_package CYGPKG_DEVS_ETH_POWERPC_MOAB {
+    display       "TAMS MOAB (PPC405GPr) ethernet support"
+    description   "Hardware specifics for TAMS MOAB ethernet"
+
+    parent        CYGPKG_IO_ETH_DRIVERS
+    active_if	  CYGPKG_IO_ETH_DRIVERS
+    active_if	  CYGPKG_HAL_POWERPC 
+    active_if	  CYGPKG_HAL_POWERPC_PPC40x
+
+    requires      CYGPKG_DEVS_ETH_POWERPC_PPC405
+    requires      CYGHWR_DEVS_ETH_PHY_DP83847
+    requires      CYGPKG_HAL_POWERPC_MOAB
+
+    cdl_option CYGHWR_DEVS_ETH_POWERPC_MOAB_ETH0 {
+        display       "Include eth0 ethernet device"
+        default_value 1
+        description   "
+          This option controls whether a driver for eth0
+          is included in the resulting system."
+        implements    CYGHWR_NET_DRIVERS
+        implements    CYGHWR_NET_DRIVER_ETH0
+        implements    CYGHWR_DEVS_ETH_POWERPC_PPC405_NET_DRIVERS
+    }
+
+    cdl_option CYGHWR_DEVS_ETH_POWERPC_MOAB_ETH1 {
+        display       "Include eth1 ethernet device"
+        default_value 1
+        description   "
+          This option controls whether a driver for eth1
+          is included in the resulting system."
+        implements    CYGHWR_NET_DRIVERS
+        implements    CYGHWR_NET_DRIVER_ETH1
+        requires      CYGHWR_DEVS_ETH_POWERPC_MOAB_ETH0
+    }
+
+    include_dir   cyg/io
+
+    define_proc {
+        puts $::cdl_system_header "#define CYGDAT_DEVS_PPC405_ETH_CDL <pkgconf/devs_eth_powerpc_moab.h>"
+        puts $::cdl_system_header "#define CYGDAT_DEVS_PPC405_ETH_INL <cyg/io/moab_eth.inl>"
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/moab/current/include/moab_eth.inl
@@ -0,0 +1,120 @@
+#ifndef CYGONCE_DEVS_MOAB_ETH_INL
+#define CYGONCE_DEVS_MOAB_ETH_INL
+//==========================================================================
+//
+//      moab_eth.inl
+//
+//      Hardware specifics for TAMS MOAB ethernet support
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: gthomas
+// Date:         2003-08-19
+// Purpose:      
+// Description:  
+//              
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include CYGDAT_DEVS_PPC405_ETH_CDL
+
+#ifdef CYGHWR_DEVS_ETH_POWERPC_MOAB_ETH0
+ETH_PHY_REG_LEVEL_ACCESS_FUNS(eth0_phy, 
+                              ppc405_eth_phy_init,
+                              NULL,
+                              ppc405_eth_phy_put_reg,
+                              ppc405_eth_phy_get_reg);
+
+// Align buffers on a cache boundary
+#define RxBUFSIZE CYGNUM_DEVS_ETH_POWERPC_PPC405_RxNUM*CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE
+#define TxBUFSIZE CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM*CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE
+static unsigned char ppc405_eth_rxbufs[RxBUFSIZE] __attribute__((aligned(HAL_DCACHE_LINE_SIZE)));
+static unsigned char ppc405_eth_txbufs[TxBUFSIZE] __attribute__((aligned(HAL_DCACHE_LINE_SIZE)));
+static mal_bd_t ppc405_eth_rxbd[CYGNUM_DEVS_ETH_POWERPC_PPC405_RxNUM] __attribute__((aligned(HAL_DCACHE_LINE_SIZE)));
+static mal_bd_t ppc405_eth_txbd[CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM] __attribute__((aligned(HAL_DCACHE_LINE_SIZE)));
+
+static struct ppc405_eth_info ppc405_eth0_info = {
+    0, // Interrupt vector
+    "eth0_esa",
+    { 0x08, 0x00, 0x3C, 0x28, 0x7A, 0xBA}, // Default ESA
+    CYGNUM_DEVS_ETH_POWERPC_PPC405_RxNUM,  // Number of Rx buffers
+    ppc405_eth_rxbufs,                     // Rx buffer space
+    ppc405_eth_rxbd,                       // Rx buffer headers
+    CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM,  // Number of Tx buffers
+    ppc405_eth_txbufs,                     // Tx buffer space
+    ppc405_eth_txbd,                       // Tx buffer headers
+    &eth0_phy,                             // PHY access routines
+};
+
+ETH_DRV_SC(ppc405_eth0_sc,
+           &ppc405_eth0_info,  // Driver specific data
+           "eth0",             // Name for this interface
+           ppc405_eth_start,
+           ppc405_eth_stop,
+           ppc405_eth_control,
+           ppc405_eth_can_send,
+           ppc405_eth_send,
+           ppc405_eth_recv,
+           ppc405_eth_deliver,
+           ppc405_eth_int,
+           ppc405_eth_int_vector);
+
+NETDEVTAB_ENTRY(ppc405_netdev, 
+                "ppc405_eth", 
+                ppc405_eth_init, 
+                &ppc405_eth0_sc);
+
+#ifdef CYGPKG_REDBOOT
+#include <pkgconf/redboot.h>
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
+#include <redboot.h>
+#include <flash_config.h>
+RedBoot_config_option("Network hardware address [MAC]",
+                      eth0_esa,
+                      ALWAYS_ENABLED, true,
+                      CONFIG_ESA, &ppc405_eth0_info.enaddr
+    );
+#endif // CYGSEM_REDBOOT_FLASH_CONFIG
+#endif // CYGPKG_REDBOOT
+
+#endif // CYGHWR_DEVS_ETH_POWERPC_MOAB_ETH0
+
+#endif  // CYGONCE_DEVS_MOAB_ETH_INL
+// ------------------------------------------------------------------------
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/ppc405/current/ChangeLog
@@ -0,0 +1,44 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/ppc405_enet.h: 
+	* src/if_ppc405.c: 
+	* cdl/ppc405_eth_drivers.cdl: New package - generic ethernet driver
+	for PowerPC 405GP based boards.
+
+//===========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//===========================================================================
+	
+	
+
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/ppc405/current/cdl/ppc405_eth_drivers.cdl
@@ -0,0 +1,143 @@
+# ====================================================================
+#
+#      ppc405_eth_drivers.cdl
+#
+#      Ethernet drivers for PowerPC 405GP based platforms
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      gthomas
+# Original data:  gthomas
+# Contributors:
+# Date:           2003-08-15
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_DEVS_ETH_POWERPC_PPC405 {
+    display       "PPC405 ethernet driver"
+
+    parent        CYGPKG_IO_ETH_DRIVERS
+    active_if	  CYGPKG_IO_ETH_DRIVERS
+    active_if	  CYGPKG_HAL_POWERPC 
+    active_if	  CYGPKG_HAL_POWERPC_PPC40x
+    requires      { CYGHWR_HAL_POWERPC_PPC4XX == "405GP" }
+    requires      CYGPKG_DEVS_ETH_PHY
+
+    implements    CYGHWR_NET_DRIVERS
+    implements    CYGHWR_NET_DRIVER_ETH0
+    implements    CYGINT_IO_ETH_MULTICAST
+    include_dir   .
+    include_files ; # none _exported_ whatsoever
+
+    # Debug I/O during network stack initialization is not reliable
+    requires { !CYGPKG_NET || CYGPKG_NET_FORCE_SERIAL_CONSOLE == 1 }
+
+    cdl_interface CYGHWR_DEVS_ETH_POWERPC_PPC405_NET_DRIVERS {
+        display "Network drivers"
+    }
+    requires { CYGHWR_DEVS_ETH_POWERPC_PPC405_NET_DRIVERS == 1 }
+
+    description   "Ethernet driver for PowerPC 405GP boards."
+    compile       -library=libextras.a if_ppc405.c
+
+    cdl_option CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE {
+        display       "Buffer size"
+        flavor        data
+        default_value 1520
+        description   "
+            This option specifies the size of the internal buffers used
+            for the PowerPC PPC405/ethernet device."
+    }
+
+    cdl_option CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM {
+        display       "Number of output buffers"
+        flavor        data
+        legal_values  2 to 64
+        default_value 16
+        description   "
+            This option specifies the number of output buffer packets
+            to be used for the PowerPC PPC405/ethernet device."
+    }
+
+    cdl_option CYGNUM_DEVS_ETH_POWERPC_PPC405_RxNUM {
+        display       "Number of input buffers"
+        flavor        data
+        legal_values  2 to 64
+        default_value 16
+        description   "
+            This option specifies the number of input buffer packets
+            to be used for the PowerPC PPC405/ethernet device."
+    }
+
+    cdl_component CYGSEM_DEVS_ETH_POWERPC_PPC405_RESET_PHY {
+        display "Reset and reconfigure PHY"
+        flavor  bool
+        default_value { CYG_HAL_STARTUP != "RAM" }
+        description "
+            This option allows control over the physical transceiver"
+
+        cdl_option CYGNUM_DEVS_ETH_POWERPC_PPC405_LINK_MODE {
+            display       "Initial link mode"
+            flavor        data
+            legal_values  { "10Mb" "100Mb" "Auto" }
+            default_value { "Auto" }
+            description   "
+                This option specifies initial mode for the physical
+                link.  The PHY will be reset and then set to this mode."
+        }
+    }
+
+    cdl_component CYGPKG_DEVS_ETH_POWERPC_PPC405_OPTIONS {
+        display "PPC405 ethernet driver build options"
+        flavor  none
+	no_define
+
+        cdl_option CYGPKG_DEVS_ETH_POWERPC_PPC405_CFLAGS_ADD {
+            display "Additional compiler flags"
+            flavor  data
+            no_define
+            default_value { "-D_KERNEL -D__ECOS" }
+            description   "
+                This option modifies the set of compiler flags for
+                building the PPC405 ethernet driver package. These flags are used in addition
+                to the set of global flags."
+        }
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/ppc405/current/src/if_ppc405.c
@@ -0,0 +1,672 @@
+//==========================================================================
+//
+//      dev/if_ppc405.c
+//
+//      Ethernet device driver for PowerPC PPC405 boards
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: gthomas
+// Date:         2003-08-15
+// Purpose:      
+// Description:  hardware driver for PPC405
+//              
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+// Ethernet device driver for PPC405
+
+#include <pkgconf/system.h>
+#include <pkgconf/devs_eth_powerpc_ppc405.h>
+#include <pkgconf/io_eth_drivers.h>
+
+#ifdef CYGPKG_NET
+#include <pkgconf/net.h>
+#endif
+
+#include <cyg/infra/cyg_type.h>
+#include <cyg/infra/diag.h>
+
+#include <cyg/hal/hal_arch.h>
+#include <cyg/hal/hal_cache.h>
+#include <cyg/hal/hal_intr.h>
+#include <cyg/hal/drv_api.h>
+#include <cyg/hal/hal_if.h>
+#include <cyg/hal/ppc_regs.h>
+
+#include <cyg/io/eth/netdev.h>
+#include <cyg/io/eth/eth_drv.h>
+#include <cyg/io/eth_phy.h>
+
+//
+// PHY access functions
+//
+static void ppc405_eth_phy_init(void);
+static void ppc405_eth_phy_put_reg(int reg, int phy, unsigned short data);
+static bool ppc405_eth_phy_get_reg(int reg, int phy, unsigned short *val);
+
+#include "ppc405_enet.h"
+#include CYGDAT_DEVS_PPC405_ETH_INL
+
+#define os_printf diag_printf
+
+// For fetching the ESA from RedBoot
+#include <cyg/hal/hal_if.h>
+#ifndef CONFIG_ESA
+#define CONFIG_ESA 6
+#endif
+
+static void          ppc405_eth_int(struct eth_drv_sc *data);
+
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+
+static cyg_interrupt ppc405_emac_interrupt;
+static cyg_handle_t  ppc405_emac_interrupt_handle;
+static cyg_interrupt ppc405_mal_txeob_interrupt;
+static cyg_handle_t  ppc405_mal_txeob_interrupt_handle;
+static cyg_interrupt ppc405_mal_rxeob_interrupt;
+static cyg_handle_t  ppc405_mal_rxeob_interrupt_handle;
+static cyg_interrupt ppc405_mal_txde_interrupt;
+static cyg_handle_t  ppc405_mal_txde_interrupt_handle;
+static cyg_interrupt ppc405_mal_rxde_interrupt;
+static cyg_handle_t  ppc405_mal_rxde_interrupt_handle;
+static cyg_interrupt ppc405_mal_serr_interrupt;
+static cyg_handle_t  ppc405_mal_serr_interrupt_handle;
+
+#define EMAC_INTERRUPT_HANDLER(_int_,_hdlr_)                                                    \
+    cyg_drv_interrupt_create(_int_,                                                             \
+                             0,                                                                 \
+                             (cyg_addrword_t)sc, /*  Data item passed to interrupt handler */   \
+                             (cyg_ISR_t *)ppc405_eth_isr,                                       \
+                             (cyg_DSR_t *)eth_drv_dsr,                                          \
+                             &ppc405_##_hdlr_##_interrupt_handle,                               \
+                             &ppc405_##_hdlr_##_interrupt);                                     \
+    cyg_drv_interrupt_attach(ppc405_##_hdlr_##_interrupt_handle);                               \
+    cyg_drv_interrupt_acknowledge(_int_);                                                       \
+    cyg_drv_interrupt_unmask(_int_);
+
+// This ISR is called when the ethernet interrupt occurs
+static int
+ppc405_eth_isr(cyg_vector_t vector, cyg_addrword_t data, HAL_SavedRegisters *regs)
+{
+    struct eth_drv_sc *sc = (struct eth_drv_sc *)data;
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_MAL_SERR);
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_MAL_TX_EOB);
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_MAL_RX_EOB);
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_MAL_TX_DE);
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_MAL_RX_DE);
+    cyg_drv_interrupt_mask(CYGNUM_HAL_INTERRUPT_EMAC0);
+    qi->ints = vector;
+    return (CYG_ISR_HANDLED|CYG_ISR_CALL_DSR);  // Run the DSR
+}
+#endif
+
+// Deliver function (ex-DSR) handles the ethernet [logical] processing
+static void
+ppc405_eth_deliver(struct eth_drv_sc *sc)
+{
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    cyg_uint32 old_ints;
+#endif
+    ppc405_eth_int(sc);
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+    // Allow interrupts to happen again
+    HAL_DISABLE_INTERRUPTS(old_ints);
+    cyg_drv_interrupt_acknowledge(qi->ints);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_MAL_SERR);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_MAL_TX_EOB);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_MAL_RX_EOB);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_MAL_TX_DE);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_MAL_RX_DE);
+    cyg_drv_interrupt_unmask(CYGNUM_HAL_INTERRUPT_EMAC0);
+    HAL_RESTORE_INTERRUPTS(old_ints);
+#endif
+}
+
+//
+// PHY unit access
+//
+static void 
+ppc405_eth_phy_init(void)
+{
+    // Set up MII hardware - nothing to do on this platform
+}
+
+static void 
+ppc405_eth_phy_put_reg(int reg, int phy, unsigned short data)
+{
+    unsigned long reg_val;
+
+    reg_val = EMAC0_STACR_STAC_WRITE | EMAC0_STACR_OPBC_66;
+    reg_val |= (phy << EMAC0_STACR_PCDA_SHIFT) | reg;
+    reg_val |= (data << EMAC0_STACR_PHYD_SHIFT);
+#ifdef PHY_DEBUG
+    os_printf("PHY PUT - reg: %d, phy: %d, val: %04x [%08x]\n", reg, phy, data, reg_val);
+#endif
+    while ((EMAC0_STACR & EMAC0_STACR_OC) == 0) ;  // Wait for MII free
+    EMAC0_STACR = reg_val;
+    while ((EMAC0_STACR & EMAC0_STACR_OC) == 0) ;  // Wait for MII complete
+}
+
+static bool 
+ppc405_eth_phy_get_reg(int reg, int phy, unsigned short *val)
+{
+    unsigned long reg_val;
+
+    reg_val = EMAC0_STACR_STAC_READ | EMAC0_STACR_OPBC_66;
+    reg_val |= (phy << EMAC0_STACR_PCDA_SHIFT) | reg;
+#ifdef PHY_DEBUG
+    os_printf("PHY GET - reg: %d, phy: %d [%08x] = ", reg, phy, reg_val);
+#endif
+    while ((EMAC0_STACR & EMAC0_STACR_OC) == 0) ;  // Wait for MII free
+    EMAC0_STACR = reg_val;
+    while ((EMAC0_STACR & EMAC0_STACR_OC) == 0) ;  // Wait for MII complete
+    if ((EMAC0_STACR & EMAC0_STACR_PHYE) == 0) {
+        // Operation completed with no error
+        *val = (EMAC0_STACR & EMAC0_STACR_PHYD) >> EMAC0_STACR_PHYD_SHIFT;
+#ifdef PHY_DEBUG
+        os_printf("%04x\n", *val);
+#endif
+        return true;
+    } else {
+        // No response
+#ifdef PHY_DEBUG
+        os_printf("***ERROR***\n");
+#endif
+        return false;
+    }
+}
+
+//
+// [re]Initialize the ethernet controller
+//   Done separately since shutting down the device requires a 
+//   full reconfiguration when re-enabling.
+//   when 
+static bool
+ppc405_eth_reset(struct eth_drv_sc *sc, unsigned char *enaddr, int flags)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    volatile mal_bd_t *rxbd, *RxBD, *txbd, *TxBD;
+    unsigned char *RxBUF, *TxBUF;
+    int i, int_state;
+    unsigned long mal_status, mode;
+    unsigned short phy_state = 0;
+
+    // Ignore unless device is idle/stopped
+    if ((EMAC0_MR0 & (EMAC0_MR0_RXI|EMAC0_MR0_TXI)) != (EMAC0_MR0_RXI|EMAC0_MR0_TXI)) {
+        return true;
+    }
+
+    // Make sure interrupts are off while we mess with the device
+    HAL_DISABLE_INTERRUPTS(int_state);
+
+    // Reset EMAC controller
+    EMAC0_MR0 |= EMAC0_MR0_SRST;
+    i = 0;
+    while ((EMAC0_MR0 & EMAC0_MR0_SRST) != 0) {
+        if (++i >= 500000) {
+            os_printf("PPC405 Ethernet does not reset\n");
+            HAL_RESTORE_INTERRUPTS(int_state);
+            return false;
+        }
+    }
+
+    TxBD = qi->txbd_table;
+    txbd = (mal_bd_t *)CYGARC_UNCACHED_ADDRESS(TxBD);
+    RxBD = qi->rxbd_table;
+    rxbd = (mal_bd_t *)CYGARC_UNCACHED_ADDRESS(RxBD);
+    qi->tbase = qi->txbd = qi->tnext = txbd;
+    qi->rbase = qi->rxbd = qi->rnext = rxbd;
+    qi->txactive = 0;
+
+    RxBUF = qi->rxbuf;
+    TxBUF = qi->txbuf;
+
+    // setup buffer descriptors
+    for (i = 0;  i < CYGNUM_DEVS_ETH_POWERPC_PPC405_RxNUM;  i++) {
+        rxbd->length = 0;
+        rxbd->buffer = (unsigned long)RxBUF;
+        rxbd->status = MAL_BD_R | MAL_BD_I;
+        RxBUF += CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE;
+        rxbd++;
+    }
+    rxbd--;
+    rxbd->status |= MAL_BD_W;  // Last buffer
+    for (i = 0;  i < CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM;  i++) {
+        txbd->length = 0;
+        txbd->buffer = (unsigned long)TxBUF;
+        txbd->status = 0;
+        TxBUF += CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE;
+        txbd++;
+    }
+    txbd--;
+    txbd->status |= MAL_BD_W;  // Last buffer
+
+    // Tell memory access layer where the buffer descriptors are
+    CYGARC_MTDCR(MAL0_TXCARR, MAL_CASR_C0|MAL_CASR_C1);  // Disable/reset channel #0 & #1
+    CYGARC_MTDCR(MAL0_RXCARR, MAL_CASR_C0);  // Disable/reset channel #0
+    CYGARC_MTDCR(MAL0_CFG, MAL_CFG_SR);
+    i = 0;
+    CYGARC_MFDCR(MAL0_CFG, mal_status);
+    while ((mal_status & MAL_CFG_SR) != 0) {
+        if (++i >= 500000) {
+            os_printf("PPC405 MAL does not reset\n");
+            HAL_RESTORE_INTERRUPTS(int_state);
+            return false;
+        }
+    }
+    CYGARC_MTDCR(MAL0_CFG, MAL_CFG_PLBB | MAL_CFG_OPBBL | MAL_CFG_LEA | MAL_CFG_PLBT_DEFAULT);
+    CYGARC_MTDCR(MAL0_TXCTP0R, TxBD);
+    CYGARC_MTDCR(MAL0_RXCTP0R, RxBD);
+    CYGARC_MTDCR(MAL0_RXBS0, (CYGNUM_DEVS_ETH_POWERPC_PPC405_BUFSIZE/16));  // Receive buffer size
+
+    // Set device physical address (ESA)
+    EMAC0_IAHR = (enaddr[0]<<8) | (enaddr[1]<<0);
+    EMAC0_IALR = (enaddr[2]<<24) | (enaddr[3]<<16) | (enaddr[4]<<8) | (enaddr[5]<<0);
+
+    // Operating mode
+    if (!_eth_phy_init(qi->phy)) {
+        return false;
+    }
+    phy_state = _eth_phy_state(qi->phy);
+    os_printf("PPC405 ETH: ");
+    mode = EMAC0_MR1_RFS_4096 | EMAC0_MR1_TFS_2048 | EMAC0_MR1_TR0_MULTI | EMAC0_MR1_APP;
+    if ((phy_state & ETH_PHY_STAT_LINK) != 0) {
+        if ((phy_state & ETH_PHY_STAT_100MB) != 0) {
+            // Link can handle 100Mb
+            mode |= EMAC0_MR1_MF_100MB;
+            os_printf("100Mb");
+            if ((phy_state & ETH_PHY_STAT_FDX) != 0) {
+                mode |= EMAC0_MR1_FDE | EMAC0_MR1_EIFC | EMAC0_MR1_IST;
+                os_printf("/Full Duplex");
+            } 
+        } else {
+            // Assume 10Mb, half duplex
+            mode |= EMAC0_MR1_MF_10MB;
+            os_printf("10Mb");
+        }
+    } else {
+        os_printf("/***NO LINK***");
+        return false;
+    }
+    os_printf("\n");
+    EMAC0_MR1 = mode;
+
+    // Configure receiver
+    EMAC0_RMR = EMAC0_RMR_IAE | EMAC0_RMR_BAE | EMAC0_RMR_RRP | EMAC0_RMR_RFP;
+
+    // Transmit threshold to 256 bytes
+    EMAC0_TRTR = ((256/EMAC0_TRTR_TRT_SCALE)-1) << EMAC0_TRTR_TRT_SHIFT;
+
+    // Receive FIFO watermarks
+    EMAC0_RWMR = (0x1F<<EMAC0_RWMR_RLWM_SHIFT) | (0x10<<EMAC0_RWMR_RHWM_SHIFT);
+
+    // Frame gap
+    EMAC0_IPGVR = 8;
+
+    // Enable MAL
+    CYGARC_MTDCR(MAL0_TXCASR, MAL_CASR_C0);
+    CYGARC_MTDCR(MAL0_RXCASR, MAL_CASR_C0);
+
+    // Reset all interrupts
+    EMAC0_ISR = 0xFFFFFFFF;
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+    qi->ints = 0;
+#endif
+
+    // Enable interface
+    EMAC0_MR0 |= (EMAC0_MR0_RXE|EMAC0_MR0_TXE);
+
+    // Restore interrupts
+    HAL_RESTORE_INTERRUPTS(int_state);
+    return true;
+}
+
+//
+// Initialize the interface - performed at system startup
+// This function must set up the interface, including arranging to
+// handle interrupts, etc, so that it may be "started" cheaply later.
+//
+
+static bool 
+ppc405_eth_init(struct cyg_netdevtab_entry *tab)
+{
+    struct eth_drv_sc *sc = (struct eth_drv_sc *)tab->device_instance;
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    bool esa_ok;
+    unsigned char enaddr[6];
+
+    ppc405_eth_stop(sc);  // Make sure it's not running yet
+
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+    // Set up to handle interrupts
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_MAL_SERR, mal_serr);
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_MAL_TX_EOB, mal_txeob);
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_MAL_RX_EOB, mal_rxeob);
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_MAL_TX_DE, mal_txde);
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_MAL_RX_DE, mal_rxde);
+    EMAC_INTERRUPT_HANDLER(CYGNUM_HAL_INTERRUPT_EMAC0, emac);
+#endif
+
+    // Get physical device address
+#ifdef CYGPKG_REDBOOT
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
+    esa_ok = flash_get_config(qi->esa_key, enaddr, CONFIG_ESA);
+#else
+    esa_ok = false;
+#endif
+#else
+    esa_ok = CYGACC_CALL_IF_FLASH_CFG_OP(CYGNUM_CALL_IF_FLASH_CFG_GET,         
+                                         qi->esa_key, enaddr, CONFIG_ESA);
+#endif
+    if (!esa_ok) {
+        // Can't figure out ESA
+        os_printf("PPC405_ETH - Warning! ESA unknown\n");
+        memcpy(&enaddr, qi->enaddr, sizeof(enaddr));
+    }
+
+    // Configure the device
+    if (!ppc405_eth_reset(sc, enaddr, 0)) {
+        return false;
+    }
+
+    // Initialize upper level driver
+    (sc->funs->eth_drv->init)(sc, (unsigned char *)&enaddr);
+    
+    return true;
+}
+ 
+//
+// This function is called to shut down the interface.
+//
+static void
+ppc405_eth_stop(struct eth_drv_sc *sc)
+{
+    EMAC0_MR0 &= ~(EMAC0_MR0_RXE|EMAC0_MR0_TXE);
+}
+
+//
+// This function is called to "start up" the interface.  It may be called
+// multiple times, even when the hardware is already running.  It will be
+// called whenever something "hardware oriented" changes and should leave
+// the hardware ready to send/receive packets.
+//
+static void
+ppc405_eth_start(struct eth_drv_sc *sc, unsigned char *enaddr, int flags)
+{
+    EMAC0_MR0 |= (EMAC0_MR0_RXE|EMAC0_MR0_TXE);
+}
+
+//
+// This function is called for low level "control" operations
+//
+static int
+ppc405_eth_control(struct eth_drv_sc *sc, unsigned long key,
+                  void *data, int length)
+{
+    os_printf("%s.%d\n", __FUNCTION__, __LINE__);
+    return 1;
+#if 0
+#ifdef ETH_DRV_SET_MC_ALL
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    volatile struct ppc405 *ppc405 = qi->ppc405;
+#endif
+
+    switch (key) {
+    case ETH_DRV_SET_MAC_ADDRESS:
+        return 0;
+        break;
+#ifdef ETH_DRV_SET_MC_ALL
+    case ETH_DRV_SET_MC_ALL:
+    case ETH_DRV_SET_MC_LIST:
+        ppc405->RxControl &= ~RxControl_PROM;
+        ppc405->hash[0] = 0xFFFFFFFF;
+        ppc405->hash[1] = 0xFFFFFFFF;
+        return 0;
+        break;
+#endif
+    default:
+        return 1;
+        break;
+    }
+#endif
+}
+
+//
+// This function is called to see if another packet can be sent.
+// It should return the number of packets which can be handled.
+// Zero should be returned if the interface is busy and can not send any more.
+//
+static int
+ppc405_eth_can_send(struct eth_drv_sc *sc)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+
+    return (qi->txactive < CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM);
+}
+
+//
+// This routine is called to send data to the hardware.
+
+static void 
+ppc405_eth_send(struct eth_drv_sc *sc, struct eth_drv_sg *sg_list, int sg_len, 
+               int total_len, unsigned long key)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    volatile mal_bd_t *txbd;
+    volatile char *bp;
+    int i, txindex;
+
+    // Find a free buffer
+    txbd = qi->txbd;
+    // Set up buffer
+    bp = (volatile char *)CYGARC_UNCACHED_ADDRESS(txbd->buffer);
+    for (i = 0;  i < sg_len;  i++) {
+        memcpy((void *)bp, (void *)sg_list[i].buf, sg_list[i].len);
+        bp += sg_list[i].len;
+    } 
+    txbd->length = total_len;
+    txindex = ((unsigned long)txbd - (unsigned long)qi->tbase) / sizeof(*txbd);
+    qi->txkey[txindex] = key;
+    // Send it on it's way
+    txbd->status = (txbd->status & MAL_BD_W) | MAL_BD_R | MAL_BD_L | MAL_BD_I | 
+        MAL_BD_TX_GFCS | MAL_BD_TX_GPAD;
+    qi->txactive++;
+    EMAC0_TMR0 = EMAC0_TMR0_GNP0;  // Start channel 0
+    // Remember the next buffer to try
+    if (txbd->status & MAL_BD_W) {
+        qi->txbd = qi->tbase;
+    } else {
+        qi->txbd = txbd+1;
+    }
+}
+
+//
+// This function is called when a packet has been received.  It's job is
+// to prepare to unload the packet from the hardware.  Once the length of
+// the packet is known, the upper layer of the driver can be told.  When
+// the upper layer is ready to unload the packet, the internal function
+// 'ppc405_eth_recv' will be called to actually fetch it from the hardware.
+//
+static void
+ppc405_eth_RxEvent(struct eth_drv_sc *sc)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    volatile mal_bd_t *rxbd, *rxfirst;
+
+    rxbd = rxfirst = qi->rnext;
+    while ((rxbd->status & MAL_BD_R) == 0) {
+        qi->rxbd = rxbd;  // Save for callback
+        (sc->funs->eth_drv->recv)(sc, rxbd->length-4);  // Adjust for FCS
+        if (rxbd->status & MAL_BD_W) {
+            rxbd = qi->rbase;
+        } else {
+            rxbd++;
+        }
+    }
+    // Remember where we left off
+    qi->rnext = (mal_bd_t *)rxbd;
+}
+
+//
+// This function is called as a result of the "eth_drv_recv()" call above.
+// It's job is to actually fetch data for a packet from the hardware once
+// memory buffers have been allocated for the packet.  Note that the buffers
+// may come in pieces, using a scatter-gather list.  This allows for more
+// efficient processing in the upper layers of the stack.
+//
+static void
+ppc405_eth_recv(struct eth_drv_sc *sc, struct eth_drv_sg *sg_list, int sg_len)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    unsigned char *bp;
+    int i;
+
+    bp = (unsigned char *)CYGARC_UNCACHED_ADDRESS(qi->rxbd->buffer);
+    for (i = 0;  i < sg_len;  i++) {
+        if (sg_list[i].buf != 0) {
+            memcpy((void *)sg_list[i].buf, bp, sg_list[i].len);
+            bp += sg_list[i].len;
+        }
+    }
+    qi->rxbd->status = (qi->rxbd->status & (MAL_BD_W|MAL_BD_I)) | MAL_BD_R;
+}
+
+static void
+ppc405_eth_TxEvent(struct eth_drv_sc *sc)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    volatile mal_bd_t *txbd;
+    int key, txindex;
+
+    txbd = qi->tnext;
+    while ((txbd->status & (MAL_BD_R|MAL_BD_I)) == MAL_BD_I) {
+        txindex = ((unsigned long)txbd - (unsigned long)qi->tbase) / sizeof(*txbd);
+        if ((key = qi->txkey[txindex]) != 0) {
+            qi->txkey[txindex] = 0;
+            (sc->funs->eth_drv->tx_done)(sc, key, 0);
+        }
+        qi->txactive -= 1;
+        txbd->status &= MAL_BD_W;  //  Only preserve wrap bit
+        if ((txbd->status & MAL_BD_W) != 0) {
+            txbd = qi->tbase;
+        } else {
+            txbd++;
+        }
+        if (txbd == qi->tnext) {
+            break;  // Went through whole list
+        }
+    }
+    // Remember where we left off
+    qi->tnext = (mal_bd_t *)txbd;
+}
+
+//
+// Interrupt processing
+//
+int dump_mal0_esr = 0;
+
+static void          
+ppc405_eth_int(struct eth_drv_sc *sc)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    unsigned long event, tx_event, rx_event, tx_deir, rx_deir;
+
+    CYGARC_MFDCR(MAL0_TXEOBISR, tx_event);
+    if (tx_event != 0) {
+        ppc405_eth_TxEvent(sc);
+        CYGARC_MTDCR(MAL0_TXEOBISR, tx_event);
+    }
+    CYGARC_MFDCR(MAL0_RXEOBISR, rx_event);
+    if (rx_event != 0) {
+        ppc405_eth_RxEvent(sc);
+        CYGARC_MTDCR(MAL0_RXEOBISR, rx_event);
+    }
+    if ((event = EMAC0_ISR) != 0) {
+        if ((event & ~(EMAC0_ISR_SE0|EMAC0_ISR_SE1)) != 0) {
+            os_printf("EMAC0_ISR: %x\n", event);
+        }
+        if ((event & (EMAC0_ISR_TE0|EMAC0_ISR_TE1)) != 0) {
+            // Some problem with transmit
+            CYGARC_MTDCR(MAL0_TXCASR, MAL_CASR_C0);
+            qi->tnext = qi->tbase;
+        }
+        EMAC0_ISR = event;  // Reset the bits we handled
+    }
+    CYGARC_MFDCR(MAL0_ESR, event);
+    if ((event & MAL_ESR_INT_MASK) != 0) {
+        CYGARC_MFDCR(MAL0_TXDEIR, tx_deir);
+        CYGARC_MFDCR(MAL0_RXDEIR, rx_deir);
+        if (dump_mal0_esr) {
+        os_printf("MAL0_ESR: %x, Tx: %x, Rx: %x\n", event, tx_deir, rx_deir);
+        os_printf("Tx buffer headers\n");
+        diag_dump_buf((void *)qi->tbase, qi->txnum*sizeof(mal_bd_t));
+        os_printf("Rx buffer headers\n");
+        diag_dump_buf((void *)qi->rbase, qi->rxnum*sizeof(mal_bd_t));
+        }
+        if (tx_deir != 0) {
+            // Fix Tx descriptor problems
+            CYGARC_MTDCR(MAL0_TXDEIR, tx_deir);  // Clear interrupt indicator
+            CYGARC_MTDCR(MAL0_TXCASR, MAL_CASR_C0);
+            qi->tnext = qi->tbase;
+        }
+        if (rx_deir != 0) {
+            // Fix Rx descriptor problems
+            CYGARC_MTDCR(MAL0_RXDEIR, rx_deir);  // Clear interrupt indicator
+            CYGARC_MTDCR(MAL0_RXCASR, MAL_CASR_C0);
+            qi->rnext = qi->rbase;
+        }
+        CYGARC_MTDCR(MAL0_ESR, event);  // Clear events just handled
+    }
+}
+
+//
+// Interrupt vector
+//
+static int          
+ppc405_eth_int_vector(struct eth_drv_sc *sc)
+{
+    struct ppc405_eth_info *qi = (struct ppc405_eth_info *)sc->driver_private;
+    return qi->int_vector;
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/eth/powerpc/ppc405/current/src/ppc405_enet.h
@@ -0,0 +1,360 @@
+//==========================================================================
+//
+//      ppc405.h
+//
+//      PowerPC PPC405GP Ethernet
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: gthomas
+// Date:         2003-08-15
+// Purpose:      
+// Description:  
+//              
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+// PowerPC PPC405 Ethernet
+
+//
+// Ethernet MAC controller registers
+//
+#define EMAC0_MR0   *(volatile unsigned long *)0xEF600800
+#define EMAC0_MR1   *(volatile unsigned long *)0xEF600804
+#define EMAC0_TMR0  *(volatile unsigned long *)0xEF600808
+#define EMAC0_TMR1  *(volatile unsigned long *)0xEF60080C
+#define EMAC0_RMR   *(volatile unsigned long *)0xEF600810
+#define EMAC0_ISR   *(volatile unsigned long *)0xEF600814
+#define EMAC0_ISER  *(volatile unsigned long *)0xEF600818
+#define EMAC0_IAHR  *(volatile unsigned long *)0xEF60081C
+#define EMAC0_IALR  *(volatile unsigned long *)0xEF600820
+#define EMAC0_VTPID *(volatile unsigned long *)0xEF600824
+#define EMAC0_VTCI  *(volatile unsigned long *)0xEF600828
+#define EMAC0_PRT   *(volatile unsigned long *)0xEF60082C
+#define EMAC0_IAHT1 *(volatile unsigned long *)0xEF600830
+#define EMAC0_IAHT2 *(volatile unsigned long *)0xEF600834
+#define EMAC0_IAHT3 *(volatile unsigned long *)0xEF600838
+#define EMAC0_IAHT4 *(volatile unsigned long *)0xEF60083C
+#define EMAC0_GAHT1 *(volatile unsigned long *)0xEF600840
+#define EMAC0_GAHT2 *(volatile unsigned long *)0xEF600844
+#define EMAC0_GAHT3 *(volatile unsigned long *)0xEF600848
+#define EMAC0_GAHT4 *(volatile unsigned long *)0xEF60084C
+#define EMAC0_LSAH  *(volatile unsigned long *)0xEF600850
+#define EMAC0_LSAL  *(volatile unsigned long *)0xEF600854
+#define EMAC0_IPGVR *(volatile unsigned long *)0xEF600858
+#define EMAC0_STACR *(volatile unsigned long *)0xEF60085C
+#define EMAC0_TRTR  *(volatile unsigned long *)0xEF600860
+#define EMAC0_RWMR  *(volatile unsigned long *)0xEF600864
+#define EMAC0_OCTX  *(volatile unsigned long *)0xEF600868
+#define EMAC0_OCRX  *(volatile unsigned long *)0xEF60086C
+
+//
+// Mode Register 0
+//
+#define EMAC0_MR0_RXI  0x80000000  // RX MAC Idle (1 = RX is idle)
+#define EMAC0_MR0_TXI  0x40000000  // TX MAC Idle (1 = TX is idle)
+#define EMAC0_MR0_SRST 0x20000000
+#define EMAC0_MR0_TXE  0x10000000
+#define EMAC0_MR0_RXE  0x08000000
+#define EMAC0_MR0_WKE  0x04000000
+
+//
+// Mode Register 1
+//
+#define EMAC0_MR1_FDE  0x80000000
+#define EMAC0_MR1_ILE  0x40000000
+#define EMAC0_MR1_VLE  0x20000000
+#define EMAC0_MR1_EIFC 0x10000000
+#define EMAC0_MR1_APP  0x08000000
+#define EMAC0_MR1_IST  0x01000000
+#define EMAC0_MR1_MF   0x00C00000
+#define EMAC0_MR1_MF_10MB  0x00000000
+#define EMAC0_MR1_MF_100MB 0x00400000
+#define EMAC0_MR1_RFS  0x00300000
+#define EMAC0_MR1_RFS_512  0x00000000
+#define EMAC0_MR1_RFS_1024 0x00100000
+#define EMAC0_MR1_RFS_2048 0x00200000
+#define EMAC0_MR1_RFS_4096 0x00300000
+#define EMAC0_MR1_TFS  0x000C0000
+#define EMAC0_MR1_TFS_1024 0x00040000
+#define EMAC0_MR1_TFS_2048 0x00080000
+#define EMAC0_MR1_TR0  0x00018000
+#define EMAC0_MR1_TR0_SINGLE 0x00000000
+#define EMAC0_MR1_TR0_MULTI  0x00008000
+#define EMAC0_MR1_TR0_DEP    0x00010000
+#define EMAC0_MR1_TR1  0x00006000
+#define EMAC0_MR1_TR1_SINGLE 0x00000000
+#define EMAC0_MR1_TR1_MULTI  0x00002000
+#define EMAC0_MR1_TR1_DEP    0x00004000
+
+//
+// Transmit mode register 0
+//
+#define EMAC0_TMR0_GNP0  0x80000000
+#define EMAC0_TMR0_GNP1  0x40000000
+#define EMAC0_TMR0_GNPD  0x20000000
+#define EMAC0_TMR0_FC    0x10000000
+
+//
+// Transmit mode register 1
+//
+#define EMAC0_TMR1_TLR   0xF8000000
+#define EMAC0_TMR1_TLR_SHIFT (32-5)
+#define EMAC0_TMR1_TUR   0x00FF0000
+#define EMAC0_TMR1_TUR_SHIFT (32-16)
+
+//
+// Receive mode register
+//
+#define EMAC0_RMR_SP   0x80000000
+#define EMAC0_RMR_SFCS 0x40000000
+#define EMAC0_RMR_RRP  0x20000000
+#define EMAC0_RMR_RFP  0x10000000
+#define EMAC0_RMR_ROP  0x08000000
+#define EMAC0_RMR_RPIR 0x04000000
+#define EMAC0_RMR_PPP  0x02000000
+#define EMAC0_RMR_PME  0x01000000
+#define EMAC0_RMR_PMME 0x00800000
+#define EMAC0_RMR_IAE  0x00400000
+#define EMAC0_RMR_MIAE 0x00200000
+#define EMAC0_RMR_BAE  0x00100000
+#define EMAC0_RMR_MAE  0x00080000
+
+//
+// Interrupt status
+//
+#define EMAC0_ISR_OVR  0x02000000
+#define EMAC0_ISR_PP   0x01000000
+#define EMAC0_ISR_BP   0x00800000
+#define EMAC0_ISR_RP   0x00400000
+#define EMAC0_ISR_SE   0x00200000
+#define EMAC0_ISR_ALE  0x00100000
+#define EMAC0_ISR_BFCS 0x00080000
+#define EMAC0_ISR_PTLE 0x00040000
+#define EMAC0_ISR_ORE  0x00020000
+#define EMAC0_ISR_IRE  0x00010000
+#define EMAC0_ISR_DBDM 0x00000200
+#define EMAC0_ISR_DB0  0x00000100
+#define EMAC0_ISR_SE0  0x00000080
+#define EMAC0_ISR_TE0  0x00000040
+#define EMAC0_ISR_DB1  0x00000020
+#define EMAC0_ISR_SE1  0x00000010
+#define EMAC0_ISR_TE1  0x00000008
+#define EMAC0_ISR_MOS  0x00000002
+#define EMAC0_ISR_MOF  0x00000001
+
+//
+// Interrupt status enable - same as interrupt status
+//
+
+//
+// STA control register - MII interface
+//
+#define EMAC0_STACR_PHYD 0xFFFF0000
+#define EMAC0_STACR_PHYD_SHIFT (32-16)
+#define EMAC0_STACR_OC   0x00008000
+#define EMAC0_STACR_PHYE 0x00004000
+#define EMAC0_STACR_STAC 0x00003000
+#define EMAC0_STACR_STAC_READ  0x00001000
+#define EMAC0_STACR_STAC_WRITE 0x00002000
+#define EMAC0_STACR_OPBC 0x00000C00
+#define EMAC0_STACR_OPBC_50    0x00000000
+#define EMAC0_STACR_OPBC_66    0x00000400
+#define EMAC0_STACR_OPBC_83    0x00000800
+#define EMAC0_STACR_OPBC_100   0x00000C00
+#define EMAC0_STACR_PCDA 0x000003E0
+#define EMAC0_STACR_PCDA_SHIFT (32-27)
+#define EMAC0_STACR_PRA  0x0000001F
+
+//
+// Transmit request threshold
+//
+#define EMAC0_TRTR_TRT   0xF8000000   // 0=64, 1=128, 2=192, etc
+#define EMAC0_TRTR_TRT_SHIFT (32-5)
+#define EMAC0_TRTR_TRT_SCALE 64     
+
+//
+// Receive high/low water marks
+//
+#define EMAC0_RWMR_RLWM 0xFF800000
+#define EMAC0_RWMR_RLWM_SHIFT (32-9)
+#define EMAC0_RWMR_RHWM 0x0000FF80
+#define EMAC0_RWMR_RHWM_SHIFT (32-25)
+
+//
+// Memory Access Layer (MAL) - in DCR space
+//
+#define MAL0_CFG      0x180
+#define MAL0_ESR      0x181
+#define MAL0_IER      0x182
+#define MAL0_TXCASR   0x184
+#define MAL0_TXCARR   0x185
+#define MAL0_TXEOBISR 0x186
+#define MAL0_TXDEIR   0x187
+#define MAL0_RXCASR   0x190
+#define MAL0_RXCARR   0x191
+#define MAL0_RXEOBISR 0x192
+#define MAL0_RXDEIR   0x193
+#define MAL0_TXCTP0R  0x1A0
+#define MAL0_TXCTP1R  0x1A1
+#define MAL0_RXCTP0R  0x1C0
+#define MAL0_RXBS0    0x1E0
+
+//
+// MAL configuration
+//
+#define MAL_CFG_SR    0x80000000
+#define MAL_CFG_PLBP  0x00C00000
+#define MAL_CFG_PLBP_0 0x00000000
+#define MAL_CFG_PLBP_1 0x00400000
+#define MAL_CFG_PLBP_2 0x00800000
+#define MAL_CFG_PLBP_3 0x00C00000
+#define MAL_CFG_GA    0x00200000
+#define MAL_CFG_OA    0x00100000
+#define MAL_CFG_PLBLE 0x00080000
+#define MAL_CFG_PLBLT 0x00078000
+#define MAL_CFG_PLBLT_SHIFT (32-17)
+#define MAL_CFG_PLBT_DEFAULT (0x07<<MAL_CFG_PLBLT_SHIFT)
+#define MAL_CFG_PLBB  0x00004000
+#define MAL_CFG_OPBBL 0x00000080
+#define MAL_CFG_EOPIE 0x00000004
+#define MAL_CFG_LEA   0x00000002
+#define MAL_CFG_SD    0x00000001
+
+//
+// Channel active set/reset
+//
+#define MAL_CASR_C0   0x80000000
+#define MAL_CASR_C1   0x40000000
+
+//
+// Error and interrupt status
+//
+#define MAL_ESR_EVB   0x80000000
+#define MAL_ESR_CID   0x7E000000
+#define MAL_ESR_CID_SHIFT (32-7)
+#define MAL_ESR_DE    0x00100000
+#define MAL_ESR_ONE   0x00080000
+#define MAL_ESR_OTE   0x00040000
+#define MAL_ESR_OSE   0x00020000
+#define MAL_ESR_PEIN  0x00010000
+#define MAL_ESR_DEI   0x00000010
+#define MAL_ESR_ONEI  0x00000008
+#define MAL_ESR_OTEI  0x00000004
+#define MAL_ESR_OSEI  0x00000002
+#define MAL_ESR_PBEI  0x00000001
+#define MAL_ESR_INT_MASK 0x0000001F
+
+
+//
+// MAL Buffer Descriptor
+//
+typedef struct mal_bd {
+    unsigned short status;
+    unsigned short length;
+    unsigned long  buffer;
+} mal_bd_t;
+
+//
+// Status flags
+//
+#define MAL_BD_R   0x8000
+#define MAL_BD_W   0x4000
+#define MAL_BD_CM  0x2000
+#define MAL_BD_L   0x1000
+#define MAL_BD_F   0x0800
+#define MAL_BD_I   0x0400
+// EMAC TX bits (command - set before activating buffer)
+#define MAL_BD_TX_GFCS 0x0200
+#define MAL_BD_TX_GPAD 0x0100
+#define MAL_BD_TX_ISA  0x0080
+#define MAL_BD_TX_RSA  0x0040
+#define MAL_BD_TX_IVLA 0x0020
+#define MAL_BD_TX_RVLA 0x0010
+// EMAC TX bits (status - valid after buffer completes)
+#define MAL_BD_TX_BFCS 0x0200
+#define MAL_BD_TX_BPP  0x0100
+#define MAL_BD_TX_LOC  0x0080
+#define MAL_BD_TX_EDEF 0x0040
+#define MAL_BD_TX_ECOL 0x0020
+#define MAL_BD_TX_LATE 0x0010
+#define MAL_BD_TX_MULT 0x0008
+#define MAL_BD_TX_SNGL 0x0004
+#define MAL_BD_TX_URUN 0x0002
+#define MAL_BD_TX_SQE  0x0001
+// EMAC RX bits (only after buffer completes)
+#define MAL_BD_RX_ORUN 0x0200
+#define MAL_BD_RX_PP   0x0100
+#define MAL_BD_RX_BP   0x0080
+#define MAL_BD_RX_RP   0x0040
+#define MAL_BD_RX_SE   0x0020
+#define MAL_BD_RX_ALE  0x0010
+#define MAL_BD_RX_BFCS 0x0008
+#define MAL_BD_RX_PTL  0x0004
+#define MAL_BD_RX_ORNG 0x0002
+#define MAL_BD_RX_IRNG 0x0001
+
+//
+// Private information kept about interface
+//
+struct ppc405_eth_info {
+    // These fields should be defined by the implementation
+    int                 int_vector;
+    char               *esa_key;        // RedBoot 'key' for device ESA
+    unsigned char       enaddr[6];
+    int                 rxnum;          // Number of Rx buffers
+    unsigned char      *rxbuf;          // Rx buffer space
+    mal_bd_t           *rxbd_table;     // Rx buffer headers
+    int                 txnum;          // Number of Tx buffers
+    unsigned char      *txbuf;          // Tx buffer space
+    mal_bd_t           *txbd_table;     // Tx buffer headers
+    eth_phy_access_t   *phy;            // Routines to access PHY
+    // The following fields are maintained by the driver
+    volatile mal_bd_t  *txbd, *rxbd;     // Next Tx,Rx descriptor to use
+    volatile mal_bd_t  *tbase, *rbase;   // First Tx,Rx descriptor
+    volatile mal_bd_t  *tnext, *rnext;   // Next descriptor to check for interrupt
+    int                 txsize, rxsize;  // Length of individual buffers
+    int                 txactive;        // Count of active Tx buffers
+    unsigned long       txkey[CYGNUM_DEVS_ETH_POWERPC_PPC405_TxNUM];
+#ifdef CYGINT_IO_ETH_INT_SUPPORT_REQUIRED
+    unsigned long       ints;            // Mask of interrupts in progress
+#endif
+};
+
--- a/packages/devs/flash/atmel/at49xxxx/current/ChangeLog
+++ b/packages/devs/flash/atmel/at49xxxx/current/ChangeLog
@@ -1,3 +1,10 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/flash_at49xxxx_parts.inl: Add support for AT49LV040
+
+	* include/flash_at49xxxx.inl: Support devices which need "chip erase"
+	as opposed to "sector erase" operations.
+
 2003-08-08  Oyvind Harboe <oyvind.harboe@zylin.com>
 
 	* include/flash_at49xxxx.inl: the program/erase completion had a
--- a/packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx.inl
+++ b/packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx.inl
@@ -12,6 +12,7 @@
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
 // Copyright (C) 2003 Jonathan Larmour
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -70,6 +71,7 @@
 #define FLASH_Read_ID_Exit              FLASHWORD( 0xF0 )
 #define FLASH_Program                   FLASHWORD( 0xA0 )
 #define FLASH_Sector_Erase              FLASHWORD( 0x30 )
+#define FLASH_Chip_Erase                FLASHWORD( 0x10 )
 
 #define FLASH_Busy                      FLASHWORD( 0x40 ) // "Toggle" bit, I/O 6
 #define FLASH_InverseData               FLASHWORD( 0x80 ) // I/O 7, Inverse data
@@ -105,6 +107,7 @@ typedef struct flash_dev_info {
     cyg_uint32   base_mask;
     cyg_uint32   device_size;
     cyg_bool     bootblock;
+    cyg_bool     chip_erase;
     cyg_uint32   bootblocks[64];         // 0 is bootblock offset, 1-11 sub-sector sizes (or 0)
 #ifdef NOTYET // FIXME: not supported yet (use am29xxxxx for template)
     cyg_bool     banked;
@@ -307,7 +310,16 @@ flash_erase_block(void* block, unsigned 
         ROM[FLASH_Setup_Addr1] = FLASH_Setup_Erase;
         ROM[FLASH_Setup_Addr1] = FLASH_Setup_Code1;
         ROM[FLASH_Setup_Addr2] = FLASH_Setup_Code2;
-        *b_p = FLASH_Sector_Erase;
+        if (flash_dev_info->chip_erase) {
+            // Can only erase the entire device!
+            if (b_p == ROM) {
+                ROM[FLASH_Setup_Addr1] = FLASH_Chip_Erase;
+            } else {
+                res = FLASH_ERR_DRV_VERIFY;
+            }
+        } else {
+            *b_p = FLASH_Sector_Erase;
+        }
 
         size -= len;  // This much has been erased
 
--- a/packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx_parts.inl
+++ b/packages/devs/flash/atmel/at49xxxx/current/include/flash_at49xxxx_parts.inl
@@ -12,6 +12,7 @@
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
 // Copyright (C) 2003 Jonathan Larmour
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -84,6 +85,22 @@
 // #define CYGNUM_FLASH_BASE            : Address of first device
 // And select one of the below device variants
 
+#if defined(CYGPKG_DEVS_FLASH_ATMEL_AT49LV040)
+//
+// Note: this device is not terribly useful for anything other than a bootstrap device
+// as it is only 512KB and has only one erase block.
+//
+    {   // AT49LV040
+        device_id  : FLASHWORD(0x13),
+        block_size : 0x80000 * CYGNUM_FLASH_INTERLEAVE,
+        block_count: 1,
+        device_size: 0x80000 * CYGNUM_FLASH_INTERLEAVE,
+        base_mask  : ~(0x80000 * CYGNUM_FLASH_INTERLEAVE - 1),
+        bootblock  : false,
+        chip_erase : true
+    },
+#endif
+
 #if defined(CYGHWR_DEVS_FLASH_ATMEL_AT49LV8011) || \
     defined(CYGHWR_DEVS_FLASH_ATMEL_AT49BV8011)
     {   // AT49BV/LV8011
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/powerpc/moab/current/cdl/flash_moab.cdl
@@ -0,0 +1,102 @@
+# ====================================================================
+#
+#      flash_moab.cdl
+#
+#      FLASH memory - Hardware support for boot FLASH on TAMS MOAB
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Nick Garnett <nickg@calivar.com>
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      gthomas, hmt, jskov, tdrury, nickg
+# Original data:  gthomas
+# Contributors:   gthomas
+# Date:           2001-02-20
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_DEVS_FLASH_POWERPC_MOAB {
+    display       "TAMS MOAB FLASH memory support"
+    description   "FLASH memory device(s) support for MOAB board"
+
+    parent        CYGPKG_IO_FLASH
+    active_if     CYGPKG_IO_FLASH
+    requires      CYGPKG_HAL_POWERPC_MOAB
+    requires      { CYGSEM_DEVS_FLASH_POWERPC_MOAB_BOOT || CYGSEM_DEVS_FLASH_POWERPC_MOAB_MAIN }
+
+    cdl_component CYGSEM_DEVS_FLASH_POWERPC_MOAB_BOOT {
+        display       "Boot FLASH support"
+        default_value 0
+        no_define
+        description   "
+            This option enables the drivers for the bootstrap FLASH
+            device.  Note: this device is not suitable for the RedBoot
+            Flash Image System (FIS)."
+
+        compile       moab_flash.c
+    
+        # Arguably this should do in the generic package
+        # but then there is a logic loop so you can never enable it.
+        cdl_interface CYGINT_DEVS_FLASH_ATMEL_AT49XXXX_REQUIRED {
+            display   "Generic Atmel AM49XXXX driver required"
+        }
+
+        implements    CYGINT_DEVS_FLASH_ATMEL_AT49XXXX_REQUIRED
+    }
+
+    cdl_component CYGSEM_DEVS_FLASH_POWERPC_MOAB_MAIN {
+        display       "Main (NAND) FLASH support"
+        default_value 1
+        no_define
+        description   "
+            This option enables the drivers for the main FLASH
+            device.  Note: this device can be used for the RedBoot
+            Flash Image System (FIS)."
+
+        compile       moab_nand_flash.c
+
+        # Arguably this should do in the generic package
+        # but then there is a logic loop so you can never enable it.
+        cdl_interface CYGINT_DEVS_FLASH_TOSHIBA_TC58XXX_REQUIRED {
+            display   "Generic Toshiba TC58XXX driver required"
+        }
+
+        implements    CYGINT_DEVS_FLASH_TOSHIBA_TC58XXX_REQUIRED
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/powerpc/moab/current/src/moab_flash.c
@@ -0,0 +1,68 @@
+//==========================================================================
+//
+//      moab_flash.c
+//
+//      Flash programming for Atmel boot device on MOAB board
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Nick Garnett <nickg@calivar.com>
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: 
+// Date:         2003-09-19
+// Purpose:      
+// Description:  
+//              
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+
+// There's a single AT49LV040 on the MOAB board. 
+
+#define CYGPKG_DEVS_FLASH_ATMEL_AT49LV040
+#define CYGNUM_FLASH_INTERLEAVE	(1)
+#define CYGNUM_FLASH_WIDTH      (8)
+#define CYGNUM_FLASH_SERIES	(1)
+#define CYGNUM_FLASH_BASE 	(0xFFF80000u)
+
+#include <cyg/io/flash_at49xxxx.inl>
+
+
+// ------------------------------------------------------------------------
+// EOF moab_flash.c
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/powerpc/moab/current/src/moab_nand_flash.c
@@ -0,0 +1,147 @@
+//==========================================================================
+//
+//      moab_nand_flash.c
+//
+//      Flash programming for Toshiba NAND FLASH device on MOAB board
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Nick Garnett <nickg@calivar.com>
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    Gary Thomas <gary@mlbassoc.com>
+// Contributors: 
+// Date:         2003-09-02
+// Purpose:      
+// Description:  
+//              
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <cyg/infra/cyg_type.h>
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
+#include <cyg/hal/ppc_regs.h>           // Platform registers
+#include <cyg/hal/hal_io.h>             // I/O macros
+#include <cyg/hal/hal_if.h>             // Virtual vector interfaces
+
+// There's a single TC58256 on the MOAB board. 
+
+#define CYGHWR_DEVS_FLASH_TOSHIBA_TC58256
+#define CYGNUM_FLASH_INTERLEAVE	(1)
+#define CYGNUM_FLASH_WIDTH      (8)
+#define CYGNUM_FLASH_SERIES	(1)
+#define CYGNUM_FLASH_BASE 	(_MOAB_NAND)
+
+#define CYGHWR_FLASH_TC58XXX_CE   moab_CE 
+#define CYGHWR_FLASH_TC58XXX_CLE  moab_CLE 
+#define CYGHWR_FLASH_TC58XXX_ALE  moab_ALE
+#define CYGHWR_FLASH_TC58XXX_RDY  moab_RDY
+
+//
+// Select the NAND device - this will be held until the
+// entire command/data sequence has completed (which is
+// necessary for read sequential)
+//
+static void __inline__
+moab_CE(int state)
+{
+    cyg_uint32 gpio_or;
+    HAL_READ_UINT32(GPIO_OR, gpio_or);
+    if (state) {
+        // Assert CE
+        gpio_or &= ~_MOAB_CE;
+    } else {
+        // De-assert CE
+        gpio_or |= _MOAB_CE;
+    }
+    HAL_WRITE_UINT32(GPIO_OR, gpio_or);
+}
+
+//
+// Prepare to send a command byte to the NAND interface
+//
+static void __inline__
+moab_CLE(int state)
+{
+    cyg_uint32 gpio_or;
+    HAL_READ_UINT32(GPIO_OR, gpio_or);
+    if (state) {
+        // Assert CLE
+        gpio_or |= _MOAB_CLE;
+    } else {
+        // De-assert CLE
+        gpio_or &= ~_MOAB_CLE;
+    }
+    HAL_WRITE_UINT32(GPIO_OR, gpio_or);
+}
+
+//
+// Prepare to send address byte(s) to the NAND interface
+//
+static void __inline__
+moab_ALE(int state)
+{
+    cyg_uint32 gpio_or;
+
+    HAL_READ_UINT32(GPIO_OR, gpio_or);
+    if (state) {
+        // Assert ALE
+        gpio_or |= _MOAB_ALE;
+    } else {
+        // De-assert ALE
+        gpio_or &= ~_MOAB_ALE;
+    }
+    HAL_WRITE_UINT32(GPIO_OR, gpio_or);
+}
+
+//
+// Wait until the NAND device is ready (after a long operation)
+//
+static bool __inline__
+moab_RDY(void)
+{    
+    cyg_uint32 gpio_ir;
+
+    HAL_READ_UINT32(GPIO_IR, gpio_ir);
+    return ((gpio_ir & _MOAB_RDY) != 0);
+}
+
+#include <cyg/io/flash_tc58xxx.inl>
+
+
+// ------------------------------------------------------------------------
+// EOF moab_nand_flash.c
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/toshiba/tc58xxx/current/ChangeLog
@@ -0,0 +1,41 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/flash_tc58xxx_parts.inl: 
+	* include/flash_tc58xxx.inl:
+	* cdl/flash_toshiba_tc58xxx.cdl: New package - support for NAND FLASH
+	devices from Toshiba
+	
+//===========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//===========================================================================
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/toshiba/tc58xxx/current/cdl/flash_toshiba_tc58xxx.cdl
@@ -0,0 +1,68 @@
+# ====================================================================
+#
+#      flash_toshiba_tc58xxx.cdl
+#
+#      FLASH memory - Hardware support for Toshiba TC58xxx parts
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      Gary Thomas <gary@mlbassoc.com>
+# Contributors:   
+# Date:           2003-09-02
+# Description:    FLASH drivers for Toshiba TC58xxx NAND devices.  Based on
+#                 Atmel AT49xxxx drivers by Jani Monoses <jani@iv.ro>
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX {
+    display       "Toshiba TC58XXX FLASH memory support"
+    description   "FLASH memory device support for Toshiba TC58XXX"
+    parent        CYGPKG_IO_FLASH
+    active_if	  CYGPKG_IO_FLASH
+    requires      { CYGSEM_IO_FLASH_READ_INDIRECT == 1 }
+
+    active_if     CYGINT_DEVS_FLASH_TOSHIBA_TC58XXX_REQUIRED
+
+    implements    CYGHWR_IO_FLASH_DEVICE
+
+    include_dir   cyg/io
+}
+
+# EOF flash_toshiba_tc58xxx.cdl
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/toshiba/tc58xxx/current/include/flash_tc58xxx.inl
@@ -0,0 +1,422 @@
+#ifndef CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_INL
+#define CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_INL
+//==========================================================================
+//
+//      flash_tc58xxx.inl
+//
+//      Toshiba Tc58xxx series flash driver
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Jonathan Larmour
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    Gary Thomas <gary@mlbassoc.com>
+// Contributors: 
+// Date:         2003-09-02
+// Purpose:
+// Description:  FLASH drivers for Toshiba NAND FLASH TC58xxx devices.
+//               Based on Atmel AT49xxxx drivers by Jani Monoses <jani@iv.ro>
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+// FIXME!  Someday add support for ECC data & fixups of bad sectors
+
+#include <pkgconf/hal.h>
+#include <cyg/hal/hal_arch.h>
+#include <cyg/hal/hal_cache.h>
+#include CYGHWR_MEMORY_LAYOUT_H
+
+#define  _FLASH_PRIVATE_
+#include <cyg/io/flash.h>
+
+// Low level debugging
+//   1 - command level - prints messages about read/write/erase commands
+//   2 - hardware level - shows all NAND device I/O data
+#define FLASH_DEBUG  0
+
+//----------------------------------------------------------------------------
+// Common device details.
+#define FLASH_Read_ID                   FLASHWORD(0x90)
+#define FLASH_Reset                     FLASHWORD(0xFF)
+#define FLASH_Read_Mode1                FLASHWORD(0x00)
+#define FLASH_Read_Mode2                FLASHWORD(0x01)
+#define FLASH_Read_Mode3                FLASHWORD(0x50)
+#define FLASH_Program                   FLASHWORD(0x10)
+#define FLASH_Send_Data                 FLASHWORD(0x80)
+#define FLASH_Status                    FLASHWORD(0x70)
+#define FLASH_Block_Erase               FLASHWORD(0x60)
+#define FLASH_Start_Erase               FLASHWORD(0xD0)
+
+#define CYGNUM_FLASH_ID_MANUFACTURER    FLASHWORD(0x98)
+
+//----------------------------------------------------------------------------
+// Now that device properties are defined, include magic for defining
+// accessor type and constants.
+#include <cyg/io/flash_dev.h>
+
+//----------------------------------------------------------------------------
+// Information about supported devices
+typedef struct flash_dev_info {
+    flash_data_t device_id;
+    cyg_uint32   block_size;
+    cyg_uint32   page_size;
+    cyg_int32    block_count;
+    cyg_uint32   base_mask;
+    cyg_uint32   device_size;
+} flash_dev_info_t;
+
+static const flash_dev_info_t* flash_dev_info;
+static const flash_dev_info_t supported_devices[] = {
+#include <cyg/io/flash_tc58xxx_parts.inl>
+};
+#define NUM_DEVICES (sizeof(supported_devices)/sizeof(flash_dev_info_t))
+
+//----------------------------------------------------------------------------
+// Functions that put the flash device into non-read mode must reside
+// in RAM.
+void flash_query(void* data) __attribute__ ((section (".2ram.flash_query")));
+int  flash_erase_block(void* block, unsigned int size)
+    __attribute__ ((section (".2ram.flash_erase_block")));
+int  flash_program_buf(void* addr, void* data, int len)
+    __attribute__ ((section (".2ram.flash_program_buf")));
+
+//----------------------------------------------------------------------------
+// Initialize driver details
+int
+flash_hwr_init(void)
+{
+    flash_data_t id[4];
+    int i;
+
+#ifdef CYGHWR_FLASH_TC58XXX_PLF_INIT
+    CYGHWR_FLASH_TC58XXX_PLF_INIT();
+#endif
+
+    flash_dev_query(id);
+
+    // Check that flash_id data is matching the one the driver was
+    // configured for.
+
+    // Check manufacturer
+    if (id[0] != CYGNUM_FLASH_ID_MANUFACTURER) {
+        diag_printf("Can't identify FLASH - manufacturer is: %x, should be %x\n", 
+                    id[0], CYGNUM_FLASH_ID_MANUFACTURER);
+        return FLASH_ERR_DRV_WRONG_PART;
+    }
+
+    // Look through table for device data
+    flash_dev_info = supported_devices;
+    for (i = 0; i < NUM_DEVICES; i++) {
+        if (flash_dev_info->device_id == id[1])
+            break;
+        flash_dev_info++;
+    }
+
+    // Did we find the device? If not, return error.
+    if (NUM_DEVICES == i) {
+        diag_printf("Can't identify FLASH - device is: %x, supported: ", id[1]);
+        for (i = 0;  i < NUM_DEVICES;  i++) {
+            diag_printf("%x ", supported_devices[i].device_id);
+        }
+        diag_printf("\n");
+        return FLASH_ERR_DRV_WRONG_PART;
+    }
+
+    // Fill in device details
+    flash_info.block_size = flash_dev_info->block_size;
+    flash_info.blocks = flash_dev_info->block_count * CYGNUM_FLASH_SERIES;
+    flash_info.start = (void *)CYGNUM_FLASH_BASE;
+    flash_info.end = (void *)(CYGNUM_FLASH_BASE+ (flash_dev_info->device_size * CYGNUM_FLASH_SERIES));
+    return FLASH_ERR_OK;
+}
+
+//----------------------------------------------------------------------------
+// Map a hardware status to a package error
+int
+flash_hwr_map_error(int e)
+{
+    return e;
+}
+
+
+//----------------------------------------------------------------------------
+// See if a range of FLASH addresses overlaps currently running code
+bool
+flash_code_overlaps(void *start, void *end)
+{
+    extern unsigned char _stext[], _etext[];
+
+    return ((((unsigned long)&_stext >= (unsigned long)start) &&
+             ((unsigned long)&_stext < (unsigned long)end)) ||
+            (((unsigned long)&_etext >= (unsigned long)start) &&
+             ((unsigned long)&_etext < (unsigned long)end)));
+}
+
+static void
+put_NAND(volatile flash_data_t *ROM, flash_data_t val)
+{
+    *ROM = val;
+#if FLASH_DEBUG > 1
+    diag_printf("%02x ", val);
+#endif
+}
+
+//----------------------------------------------------------------------------
+// Flash Query
+//
+// Only reads the manufacturer and part number codes for the first
+// device(s) in series. It is assumed that any devices in series
+// will be of the same type.
+
+void
+flash_query(void* data)
+{
+    flash_data_t* id = (flash_data_t*) data;
+    volatile flash_data_t *ROM;
+
+    ROM = (volatile flash_data_t*) CYGNUM_FLASH_BASE;
+    // Send initial RESET command
+    CYGHWR_FLASH_TC58XXX_CE(1);
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Reset);
+    CYGHWR_FLASH_TC58XXX_CLE(0);
+    CYGHWR_FLASH_TC58XXX_CE(0);
+    // Now, wait for a good while
+    CYGACC_CALL_IF_DELAY_US(10000);  // Actually 10ms
+    // Issue device query
+    CYGHWR_FLASH_TC58XXX_CE(1);
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Read_ID);
+    CYGHWR_FLASH_TC58XXX_CLE(0);
+    CYGHWR_FLASH_TC58XXX_ALE(1);
+    put_NAND(ROM, 0x00);  // Dummy address
+    CYGHWR_FLASH_TC58XXX_ALE(0);
+    // Minimum 100ns delay after deasserting ALE
+    CYGACC_CALL_IF_DELAY_US(10);  // Actually 10us
+    id[0] = *ROM;
+    id[1] = *ROM;
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Reset);
+    CYGHWR_FLASH_TC58XXX_CLE(0);
+    CYGHWR_FLASH_TC58XXX_CE(0);
+}
+
+//----------------------------------------------------------------------------
+// Erase Block
+int
+flash_erase_block(void* block, unsigned int size)
+{
+    volatile flash_data_t* ROM;
+    volatile flash_data_t* b_p = (volatile flash_data_t*) block;
+    int res = FLASH_ERR_OK;
+    int len = 0;
+    int cnt = 0;
+    flash_data_t stat;
+
+#if FLASH_DEBUG > 0
+    diag_printf("%s - block: %x, size: %d\n", __FUNCTION__, block, size);
+#endif
+    ROM = (volatile flash_data_t*) CYGNUM_FLASH_BASE;
+    // Erase the next block
+#if FLASH_DEBUG > 1
+    diag_printf("<< ");
+#endif
+    CYGHWR_FLASH_TC58XXX_CE(1);
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Block_Erase);
+    CYGHWR_FLASH_TC58XXX_CLE(0);
+    CYGHWR_FLASH_TC58XXX_ALE(1);
+    put_NAND(ROM, ((unsigned long)b_p & 0x0001FE00) >> 9);     // A9..A16
+    put_NAND(ROM, ((unsigned long)b_p & 0x01FE0000) >> 17);  // A17..A24
+    CYGHWR_FLASH_TC58XXX_ALE(0);
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Start_Erase);
+    CYGHWR_FLASH_TC58XXX_CLE(0);        
+    while (!CYGHWR_FLASH_TC58XXX_RDY()) cnt++;  // Wait for operation to complete
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    put_NAND(ROM, FLASH_Status);
+    CYGHWR_FLASH_TC58XXX_CLE(0);        
+    stat = *ROM;
+    CYGHWR_FLASH_TC58XXX_CE(0);
+#if FLASH_DEBUG > 1
+    diag_printf(">>\n");
+#endif
+#if FLASH_DEBUG > 0
+    diag_printf("block: %x, stat: %x, count = %d\n", b_p, stat, cnt);
+#endif
+    return res;
+}
+
+//----------------------------------------------------------------------------
+// Program Buffer
+int
+flash_program_buf(void* addr, void* data, int len)
+{
+    volatile flash_data_t* ROM;
+    volatile flash_data_t* addr_ptr = (volatile flash_data_t*) addr;
+    volatile flash_data_t* data_ptr = (volatile flash_data_t*) data;
+    int res = FLASH_ERR_OK;
+
+    int i;
+    int cnt;
+    flash_data_t stat;
+
+    ROM = (volatile flash_data_t*) CYGNUM_FLASH_BASE;
+#if FLASH_DEBUG > 0
+    diag_printf("%s - addr: %x, data: %x, len: %d, FLASH: %p/%d\n", 
+                __FUNCTION__, addr, data, len, ROM, sizeof(flash_data_t));
+#endif
+    while (len > 0) {
+        CYGHWR_FLASH_TC58XXX_CE(1);
+        CYGHWR_FLASH_TC58XXX_CLE(1);
+#if FLASH_DEBUG > 1
+        diag_printf("<< ");
+#endif
+        put_NAND(ROM, FLASH_Read_Mode1);
+        put_NAND(ROM, FLASH_Send_Data);
+        CYGHWR_FLASH_TC58XXX_CLE(0);
+        CYGHWR_FLASH_TC58XXX_ALE(1);
+        put_NAND(ROM, ((unsigned long)addr_ptr & 0x000000FF) >> 0);   // A0..A7
+        put_NAND(ROM, ((unsigned long)addr_ptr & 0x0001FE00) >> 9);   // A9..A16
+        put_NAND(ROM, ((unsigned long)addr_ptr & 0x01FE0000) >> 17);  // A17..A24
+        CYGHWR_FLASH_TC58XXX_ALE(0);
+#if FLASH_DEBUG > 1
+        diag_printf(">>\n");
+#endif
+        // Move one page of data to buffer
+        for (i = 0;  i < 512;  i++) {
+            put_NAND(ROM, *data_ptr++);
+#if FLASH_DEBUG > 1
+            if ((i % 16) == 15) diag_printf("\n");
+#endif
+        }
+        // OOB data
+        for (i = 0;  i < 16;  i++) {
+            put_NAND(ROM, 0xFF);
+#if FLASH_DEBUG > 1
+            if ((i % 16) == 15) diag_printf("\n");
+#endif
+        }
+#if FLASH_DEBUG > 1
+        diag_printf("<< ");
+#endif
+        CYGHWR_FLASH_TC58XXX_CLE(1);
+        put_NAND(ROM, FLASH_Program);
+        CYGHWR_FLASH_TC58XXX_CLE(0);
+        CYGACC_CALL_IF_DELAY_US(1);  // Actually 200ns
+        cnt = 0;
+        while (!CYGHWR_FLASH_TC58XXX_RDY()) cnt++;  // Wait for page data to be ready
+        CYGHWR_FLASH_TC58XXX_CLE(1);
+        put_NAND(ROM, FLASH_Status);
+        CYGHWR_FLASH_TC58XXX_CLE(0);        
+#if FLASH_DEBUG > 1
+        diag_printf(">>\n");
+#endif
+        stat = *ROM;
+        CYGHWR_FLASH_TC58XXX_CE(0);        
+#if FLASH_DEBUG > 0
+        diag_printf("program at %x, stat: %x, count = %d\n", addr_ptr, stat, cnt);
+#endif
+        addr_ptr += 512;  len -= 512;
+    }
+    return res;
+}
+
+//----------------------------------------------------------------------------
+// Read data into buffer
+int
+flash_read_buf(void* addr, void* data, int len)
+{
+    volatile flash_data_t* ROM;
+    volatile flash_data_t  dummy;
+    volatile flash_data_t* addr_ptr = (volatile flash_data_t*) addr;
+    volatile flash_data_t* data_ptr = (volatile flash_data_t*) data;
+    int res = FLASH_ERR_OK;
+    int i;
+    int cnt;
+
+    ROM = (volatile flash_data_t*) CYGNUM_FLASH_BASE;
+#if FLASH_DEBUG > 1
+    diag_printf("<< ");
+#endif
+    CYGHWR_FLASH_TC58XXX_CE(1);
+    CYGHWR_FLASH_TC58XXX_CLE(1);
+    if (((unsigned long)addr & 0x100) == 0) {
+        // Mode 1 - reads from start of line
+        put_NAND(ROM, FLASH_Read_Mode1);
+    } else {
+        // Mode 2 - reads from second half of line
+        put_NAND(ROM, FLASH_Read_Mode2);
+    }
+    CYGHWR_FLASH_TC58XXX_CLE(0);
+    CYGHWR_FLASH_TC58XXX_ALE(1);
+    put_NAND(ROM, ((unsigned long)addr_ptr & 0x000000FF) >> 0);   // A0..A7
+    put_NAND(ROM, ((unsigned long)addr_ptr & 0x0001FE00) >> 9);   // A9..A16
+    put_NAND(ROM, ((unsigned long)addr_ptr & 0x01FE0000) >> 17);  // A17..A24
+    CYGHWR_FLASH_TC58XXX_ALE(0);
+#if FLASH_DEBUG > 1
+    diag_printf(">>\n");
+#endif
+    cnt = 0;
+    while (!CYGHWR_FLASH_TC58XXX_RDY()) cnt++;  // Wait for page data to be ready 
+#if FLASH_DEBUG > 0
+    diag_printf("Read data starting at %p, count = %d\n", data_ptr, cnt);
+#endif
+    while (len-- > 0) {
+        *data_ptr++ = *ROM;
+        if (((unsigned long)data_ptr & 0x1FF) == 0) {
+            // Data page has been read, skip over ECC/OOB data
+            for (i = 0;  i < 16;  i++) {
+                dummy = *ROM;
+            }
+            cnt = 0;
+            while (!CYGHWR_FLASH_TC58XXX_RDY()) cnt++;  // Wait for page data to be ready
+#if FLASH_DEBUG > 0
+            diag_printf("Read data starting at %p, count = %d\n", data_ptr, cnt);
+#endif
+        }
+    }
+    CYGHWR_FLASH_TC58XXX_CE(0);
+    return res;
+}
+
+#endif // CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_INL
+
+// EOF flash_tc58xxx.inl
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/toshiba/tc58xxx/current/include/flash_tc58xxx_parts.inl
@@ -0,0 +1,77 @@
+#ifndef CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_PARTS_INL
+#define CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_PARTS_INL
+//==========================================================================
+//
+//      flash_tc58xxx_parts.inl
+//
+//      Toshiba Tc58xxx series part descriptions
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Jonathan Larmour
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    Gary Thomas <gary@mlbassoc.com>
+// Contributors: 
+// Date:         2003-09-02
+// Purpose:      Should be included from the flash_tc58xxx.inl file only.
+// Description:  Toshiba Tc58xxx part descriptions
+//               Roughly based on Atmel AT49xxxx work by Jani Monoses <jani@iv.ro>
+//
+// FIXME:        Add configury for selecting bottom/top bootblocks
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+// Platform code must define the below
+// #define CYGNUM_FLASH_INTERLEAVE      : Number of interleaved devices (in parallel)
+// #define CYGNUM_FLASH_SERIES          : Number of devices in series
+// #define CYGNUM_FLASH_WIDTH           : Width of devices on platform
+// #define CYGNUM_FLASH_BASE            : Address of first device
+// And select one of the below device variants
+
+#if defined(CYGHWR_DEVS_FLASH_TOSHIBA_TC58256)
+{  // 256Mb (32MB)
+    device_id  : FLASHWORD(0x75),
+    block_size : 0x4000 * CYGNUM_FLASH_INTERLEAVE,
+    page_size  : 0x200 * CYGNUM_FLASH_INTERLEAVE,
+    block_count: 2048,
+    device_size: 0x2000000 * CYGNUM_FLASH_INTERLEAVE,
+    base_mask  : ~(0x2000000 * CYGNUM_FLASH_INTERLEAVE - 1),
+},
+#endif
+#endif // ifndef CYGONCE_DEVS_FLASH_TOSHIBA_TC58XXX_PARTS_INL
+
+// EOF flash_tc58xxx_parts.inl
--- a/packages/devs/serial/generic/16x5x/current/ChangeLog
+++ b/packages/devs/serial/generic/16x5x/current/ChangeLog
@@ -1,3 +1,11 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/ser_16x5x.c (pc_serial_init): 
+	Allow platform to define CYG_IO_SERIAL_GENERIC_16X5X_BAUD_GENERATOR if the
+	baud rate clock (values) cannot be known at compile time.  In this case,
+	the baud rate generator values are provided by platform specific code,
+	computed when the device is first initialized.
+
 2003-07-16  Jonathan Larmour  <jifl@eCosCentric.com>
 
 	* src/ser_16x5x.c (CYG_IO_SERIAL_GENERIC_16X5X_INT_PRIORITY): Add
--- a/packages/devs/serial/generic/16x5x/current/src/ser_16x5x.c
+++ b/packages/devs/serial/generic/16x5x/current/src/ser_16x5x.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -333,6 +334,27 @@ pc_serial_init(struct cyg_devtab_entry *
 {
     serial_channel *chan = (serial_channel *)tab->priv;
     pc_serial_info *ser_chan = (pc_serial_info *)chan->dev_priv;
+
+#ifdef CYG_IO_SERIAL_GENERIC_16X5X_BAUD_GENERATOR
+    // Fill in baud rate table - used for platforms where this cannot
+    // be determined statically
+    int baud_idx, baud_val;
+    if (select_baud[0] == 9999) {
+        // Table not yet initialized
+        // Assumes that 'select_baud' looks like this:
+        //   static int select_baud[] = {
+        //       9999,  -- marker
+        //       50,    -- first baud rate
+        //       110,   -- second baud rate
+        // etc.
+        for (baud_idx = 1;  baud_idx < sizeof(select_baud)/sizeof(select_baud[0]);  baud_idx++) {
+            baud_val = CYG_IO_SERIAL_GENERIC_16X5X_BAUD_GENERATOR(select_baud[baud_idx]);
+            select_baud[baud_idx] = baud_val;
+        }
+        select_baud[0] = 0;
+    }
+#endif
+
 #ifdef CYGDBG_IO_INIT
     diag_printf("16x5x SERIAL init - dev: %x.%d\n", 
                 ser_chan->base, ser_chan->int_num);
new file mode 100644
--- /dev/null
+++ b/packages/devs/serial/powerpc/ppc405/current/ChangeLog
@@ -0,0 +1,40 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/powerpc_ppc405_ser.inl: 
+	* cdl/ser_powerpc_ppc405.cdl: New package - support for PowerPC 405GP,
+	based on generic 165x5 uart.
+
+//===========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//===========================================================================
new file mode 100644
--- /dev/null
+++ b/packages/devs/serial/powerpc/ppc405/current/cdl/ser_powerpc_ppc405.cdl
@@ -0,0 +1,197 @@
+# ====================================================================
+#
+#      ser_powerpc_ppc405.cdl
+#
+#      eCos serial configuration data
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      gthomas
+# Original data:  
+# Contributors:
+# Date:           2003-09-16
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+
+cdl_package CYGPKG_IO_SERIAL_POWERPC_PPC405 {
+    display       "PowerPC PPC405 (16x5x) serial device driver"
+
+    parent        CYGPKG_IO_SERIAL_DEVICES
+    active_if     CYGPKG_IO_SERIAL
+    active_if     CYGPKG_HAL_POWERPC_PPC40x  
+# Only the 405GP has these ports
+    active_if     { CYGHWR_HAL_POWERPC_PPC4XX == "405GP" }
+
+    requires      CYGPKG_ERROR
+    include_dir   cyg/io
+
+    description   "
+           This option enables the serial 16x5x device drivers for the
+           PowerPC PPC405GP based platforms."
+
+    # FIXME: This really belongs in the GENERIC_16X5X package
+    cdl_interface CYGINT_IO_SERIAL_GENERIC_16X5X_REQUIRED {
+        display   "Generic 16x5x serial driver required"
+    }
+
+    define_proc {
+        puts $::cdl_header "#define CYGPRI_IO_SERIAL_GENERIC_16X5X_STEP 1"
+    }
+
+    define_proc {
+        puts $::cdl_system_header "/***** serial driver proc output start *****/"
+        puts $::cdl_system_header "#define CYGDAT_IO_SERIAL_GENERIC_16X5X_INL <cyg/io/powerpc_ppc405_ser.inl>"
+        puts $::cdl_system_header "#define CYGDAT_IO_SERIAL_GENERIC_16X5X_CFG <pkgconf/io_serial_powerpc_ppc405.h>"
+        puts $::cdl_system_header "/*****  serial driver proc output end  *****/"
+    }
+
+    cdl_component CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL0 {
+        display       "PowerPC PPC405GP serial port 0 driver"
+        flavor        bool
+        default_value 1
+
+        implements CYGINT_IO_SERIAL_GENERIC_16X5X_REQUIRED
+        implements CYGINT_IO_SERIAL_FLOW_CONTROL_HW
+        implements CYGINT_IO_SERIAL_LINE_STATUS_HW
+
+        description   "
+            This option includes the serial device driver for the 
+            PowerPC PPC405GP port 0."
+
+        cdl_option CYGDAT_IO_SERIAL_POWERPC_PPC405_SERIAL0_NAME {
+            display       "Device name for PowerPC PPC405GP serial port 0 driver"
+            flavor        data
+            default_value {"\"/dev/ser0\""}
+            description   "
+                This option specifies the name of the serial device
+                for the PowerPC PPC405GP port 0."
+        }
+
+        cdl_option CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BAUD {
+            display       "Baud rate for the PowerPC PPC405GP serial port 0 driver"
+            flavor        data
+            legal_values  { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400
+                            3600 4800 7200 9600 14400 19200 38400
+                            57600 115200 230400 }
+            default_value 38400
+            description   "
+                This option specifies the default baud rate (speed)
+                for the PowerPC PPC405GP port 0."
+         }
+
+         cdl_option CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BUFSIZE {
+             display       "Buffer size for the PowerPC PPC405GP serial port 0 driver"
+             flavor        data
+             legal_values  0 to 8192
+             default_value 128
+             description   "
+                 This option specifies the size of the internal
+                 buffers used for the PowerPC PPC405GP port 0."
+         }
+    }
+
+    cdl_component CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL1 {
+        display       "PowerPC PPC405GP serial port 1 driver"
+        flavor        bool
+        default_value 1
+
+        implements CYGINT_IO_SERIAL_GENERIC_16X5X_REQUIRED
+        implements CYGINT_IO_SERIAL_FLOW_CONTROL_HW
+        implements CYGINT_IO_SERIAL_LINE_STATUS_HW
+
+        description   "
+            This option includes the serial device driver for the 
+            PowerPC PPC405GP port 1."
+
+        cdl_option CYGDAT_IO_SERIAL_POWERPC_PPC405_SERIAL1_NAME {
+            display       "Device name for PowerPC PPC405GP serial port 1 driver"
+            flavor        data
+            default_value {"\"/dev/ser1\""}
+            description   "
+                This option specifies the name of the serial device
+                for the PowerPC PPC405GP port 1."
+        }
+
+        cdl_option CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BAUD {
+            display       "Baud rate for the PowerPC PPC405GP serial port 1 driver"
+            flavor        data
+            legal_values  { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400
+                            3600 4800 7200 9600 14400 19200 38400
+                            57600 115200 230400 }
+            default_value 38400
+            description   "
+                This option specifies the default baud rate (speed)
+                for the PowerPC PPC405GP port 1."
+         }
+
+         cdl_option CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BUFSIZE {
+             display       "Buffer size for the PowerPC PPC405GP serial port 1 driver"
+             flavor        data
+             legal_values  0 to 8192
+             default_value 128
+             description   "
+                 This option specifies the size of the internal
+                 buffers used for the PowerPC PPC405GP port 1."
+         }
+    }
+
+    cdl_component CYGPKG_IO_SERIAL_POWERPC_PPC405_TESTING {
+        display    "Testing parameters"
+        flavor     bool
+        default_value 1
+        no_define
+        active_if  { CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL1 }
+
+        cdl_option CYGPRI_SER_TEST_SER_DEV {
+            display       "Serial device used for testing"
+            flavor        data
+            default_value { CYGDAT_IO_SERIAL_POWERPC_PPC405_SERIAL1_NAME }
+        }
+
+        define_proc {
+            puts $::cdl_header "#define CYGPRI_SER_TEST_CRASH_ID \"PPC405GP\""
+            puts $::cdl_header "#define CYGPRI_SER_TEST_TTY_DEV  \"/dev/tty1\""
+        }
+    }
+
+}
+
+# EOF ser_powerpc_ppc405.cdl
new file mode 100644
--- /dev/null
+++ b/packages/devs/serial/powerpc/ppc405/current/include/powerpc_ppc405_ser.inl
@@ -0,0 +1,167 @@
+//==========================================================================
+//
+//      io/serial/powerpc/powerpc_ppc405_ser.inl
+//
+//      PPC405GP Serial I/O definitions
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: 
+// Date:         2003-09-16
+// Purpose:      PowerPC PPC405GP serial drivers
+// Description: 
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <cyg/hal/hal_intr.h>
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
+#include <cyg/hal/ppc_regs.h>
+
+//-----------------------------------------------------------------------------
+// Baud rate specification
+
+static unsigned int select_baud[] = {
+    9999, // Unused -- marker
+    50,
+    75,
+    110,
+    134,
+    150,
+    200,
+    300,
+    600,
+    1200,
+    1800,
+    2400,
+    3600,
+    4800,
+    7200,
+    9600,
+    14400,
+    19200,
+    38400,
+    57600,
+    115200,
+    230400
+};
+
+externC int cyg_var_baud_generator(int baud);
+#define CYG_IO_SERIAL_GENERIC_16X5X_BAUD_GENERATOR cyg_var_baud_generator
+
+#ifdef CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL0
+static pc_serial_info ppc405_serial_info0 = {_PPC405GP_UART0, CYGNUM_HAL_INTERRUPT_UART0};
+#if CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BUFSIZE > 0
+static unsigned char ppc405_serial_out_buf0[CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BUFSIZE];
+static unsigned char ppc405_serial_in_buf0[CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BUFSIZE];
+
+static SERIAL_CHANNEL_USING_INTERRUPTS(ppc405_serial_channel0,
+                                       pc_serial_funs, 
+                                       ppc405_serial_info0,
+                                       CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BAUD),
+                                       CYG_SERIAL_STOP_DEFAULT,
+                                       CYG_SERIAL_PARITY_DEFAULT,
+                                       CYG_SERIAL_WORD_LENGTH_DEFAULT,
+                                       CYG_SERIAL_FLAGS_DEFAULT,
+                                       &ppc405_serial_out_buf0[0], sizeof(ppc405_serial_out_buf0),
+                                       &ppc405_serial_in_buf0[0], sizeof(ppc405_serial_in_buf0)
+    );
+#else
+static SERIAL_CHANNEL(ppc405_serial_channel0,
+                      pc_serial_funs, 
+                      ppc405_serial_info0,
+                      CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL0_BAUD),
+                      CYG_SERIAL_STOP_DEFAULT,
+                      CYG_SERIAL_PARITY_DEFAULT,
+                      CYG_SERIAL_WORD_LENGTH_DEFAULT,
+                      CYG_SERIAL_FLAGS_DEFAULT
+    );
+#endif
+
+DEVTAB_ENTRY(ppc405_serial_io0, 
+             CYGDAT_IO_SERIAL_POWERPC_PPC405_SERIAL0_NAME,
+             0,                     // Does not depend on a lower level interface
+             &cyg_io_serial_devio, 
+             pc_serial_init, 
+             pc_serial_lookup,     // Serial driver may need initializing
+             &ppc405_serial_channel0
+    );
+#endif //  CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL0
+
+#ifdef CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL1
+static pc_serial_info ppc405_serial_info1 = {_PPC405GP_UART1, CYGNUM_HAL_INTERRUPT_UART1};
+#if CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BUFSIZE > 0
+static unsigned char ppc405_serial_out_buf1[CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BUFSIZE];
+static unsigned char ppc405_serial_in_buf1[CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BUFSIZE];
+
+static SERIAL_CHANNEL_USING_INTERRUPTS(ppc405_serial_channel1,
+                                       pc_serial_funs, 
+                                       ppc405_serial_info1,
+                                       CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BAUD),
+                                       CYG_SERIAL_STOP_DEFAULT,
+                                       CYG_SERIAL_PARITY_DEFAULT,
+                                       CYG_SERIAL_WORD_LENGTH_DEFAULT,
+                                       CYG_SERIAL_FLAGS_DEFAULT,
+                                       &ppc405_serial_out_buf1[0], sizeof(ppc405_serial_out_buf1),
+                                       &ppc405_serial_in_buf1[0], sizeof(ppc405_serial_in_buf1)
+    );
+#else
+static SERIAL_CHANNEL(ppc405_serial_channel1,
+                      pc_serial_funs, 
+                      ppc405_serial_info1,
+                      CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_POWERPC_PPC405_SERIAL1_BAUD),
+                      CYG_SERIAL_STOP_DEFAULT,
+                      CYG_SERIAL_PARITY_DEFAULT,
+                      CYG_SERIAL_WORD_LENGTH_DEFAULT,
+                      CYG_SERIAL_FLAGS_DEFAULT
+    );
+#endif
+
+DEVTAB_ENTRY(ppc405_serial_io1, 
+             CYGDAT_IO_SERIAL_POWERPC_PPC405_SERIAL1_NAME,
+             0,                     // Does not depend on a lower level interface
+             &cyg_io_serial_devio, 
+             pc_serial_init, 
+             pc_serial_lookup,     // Serial driver may need initializing
+             &ppc405_serial_channel1
+    );
+#endif //  CYGPKG_IO_SERIAL_POWERPC_PPC405_SERIAL1
+
+// EOF powerpc_ppc405_ser.inl
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/dallas/ds1307/current/ChangeLog
@@ -0,0 +1,40 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/ds1307.cxx: 
+	* cdl/wallclock_ds1307.cdl: New package - support for DS1307 device,
+	based on DS12887 package.  Note: this is a two-wire device (I2C).
+	
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+
+
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/dallas/ds1307/current/cdl/wallclock_ds1307.cdl
@@ -0,0 +1,106 @@
+# ====================================================================
+#
+#      wallclock_ds1307.cdl
+#
+#      eCos configuration data for Dallas 1307
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      jskov
+# Contributors:   jskov
+# Date:           2001-07-06
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307 {
+    parent        CYGPKG_IO_WALLCLOCK
+    active_if     CYGPKG_IO_WALLCLOCK
+    display       "Wallclock device driver for Dallas 1307"
+    description   "
+        This package provides a file with init, get and set functions
+        for the Dallas 1307 clock part."
+
+    compile       ds1307.cxx
+
+    implements    CYGINT_WALLCLOCK_HW_IMPLEMENTATIONS
+    active_if     CYGIMP_WALLCLOCK_HARDWARE
+    implements    CYGINT_WALLCLOCK_SET_GET_MODE_SUPPORTED
+
+    cdl_option CYGIMP_WALLCLOCK_HARDWARE {
+        parent    CYGPKG_IO_WALLCLOCK_IMPLEMENTATION
+        display       "Hardware wallclock"
+        default_value 1
+        implements    CYGINT_WALLCLOCK_IMPLEMENTATIONS
+    }
+
+
+    cdl_component CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307_OPTIONS {
+        display "DS1307 wallclock build options"
+        flavor  none
+        description   "
+	    Package specific build options including control over
+	    compiler flags used only in building this package,
+	    and details of which tests are built."
+
+
+        cdl_option CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307_CFLAGS_ADD {
+            display "Additional compiler flags"
+            flavor  data
+            no_define
+            default_value { "" }
+            description   "
+                This option modifies the set of compiler flags for
+                building the wallclock device. These flags are used in addition
+                to the set of global flags."
+        }
+
+        cdl_option CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307_CFLAGS_REMOVE {
+            display "Suppressed compiler flags"
+            flavor  data
+            no_define
+            default_value { "" }
+            description   "
+                This option modifies the set of compiler flags for
+                building the wallclock device. These flags are removed from
+                the set of global flags if present."
+        }
+
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/dallas/ds1307/current/src/ds1307.cxx
@@ -0,0 +1,237 @@
+//==========================================================================
+//
+//      devs/wallclock/ds1307.inl
+//
+//      Wallclock implementation for Dallas 1307
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):     gthomas
+// Contributors:  
+// Date:          2003-09-19
+// Purpose:       Wallclock driver for Dallas 1307
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <pkgconf/hal.h>                // Platform specific configury
+#include <pkgconf/wallclock.h>          // Wallclock device config
+
+#include <cyg/hal/hal_io.h>             // IO macros
+#include <cyg/hal/hal_intr.h>           // interrupt enable/disable
+#include <cyg/infra/cyg_type.h>         // Common type definitions and support
+
+#include <cyg/io/wallclock.hxx>         // The WallClock API
+#include <cyg/io/wallclock/wallclock.inl> // Helpers
+
+#include <cyg/infra/diag.h>
+
+//#define DEBUG
+
+// Registers
+#define DS_SECONDS         0x00
+#define DS_MINUTES         0x01
+#define DS_HOURS           0x02
+#define DS_DOW             0x03
+#define DS_DOM             0x04
+#define DS_MONTH           0x05
+#define DS_YEAR            0x06
+#define DS_CONTROL         0x07
+#define DS_REGS_SIZE       0x08   // Size of register space
+
+#define DS_SECONDS_CH      0x80   // Clock Halt
+#define DS_HOURS_24        0x80   // 24 hour clock mode
+
+//
+// This particular chip is always accessed via I2C (2-wire protocol)
+// The platform needs to provide simple I2C access functions
+//
+// void DS_GET(cyg_uint8 *regs)
+//    Reads the entire set of registers (8 bytes) into *regs
+// void DS_PUT(cyg_uint8 *regs)
+//    Updated the entire set of registers (8 bytes) from *regs
+//
+// Using this method, the data in the registers is guaranteed to be
+// stable (if the access function manipulates the registers in an
+// single operation)
+//
+
+// Platform details
+#include CYGDAT_DEVS_WALLCLOCK_DALLAS_1307_INL
+
+//----------------------------------------------------------------------------
+// Accessor functions
+static inline void
+init_ds_hwclock(void)
+{
+    cyg_uint8 regs[DS_REGS_SIZE];
+    
+    // Verify that there are reasonable default settings - otherwise
+    // set them.
+
+    // Fetch the current state
+    DS_GET(regs);
+
+    if (0x00 == regs[DS_MONTH])
+	regs[DS_MONTH] = TO_BCD(1);
+
+    if (0x00 == regs[DS_DOW])
+	regs[DS_DOW] = TO_BCD(1);
+
+    if (0x00 == regs[DS_DOM])
+	regs[DS_DOM] = TO_BCD(1);
+
+    // Make sure clock is running and in 24 hour mode
+    regs[DS_HOURS] |= DS_HOURS_24;
+    regs[DS_SECONDS] &= ~DS_SECONDS_CH;
+
+    // Update the state
+    DS_PUT(regs);
+}
+
+
+static inline void
+set_ds_hwclock(cyg_uint32 year, cyg_uint32 month, cyg_uint32 mday,
+               cyg_uint32 hour, cyg_uint32 minute, cyg_uint32 second)
+{
+    cyg_uint8 regs[DS_REGS_SIZE];
+
+    // Set up the registers
+    regs[DS_YEAR] = TO_BCD((cyg_uint8)(year % 100));
+    regs[DS_MONTH] = TO_BCD((cyg_uint8)month);
+    regs[DS_DOM] = TO_BCD((cyg_uint8)mday);
+    regs[DS_HOURS] = TO_BCD((cyg_uint8)hour) | DS_HOURS_24;
+    regs[DS_MINUTES] = TO_BCD((cyg_uint8)minute);
+    // This also starts the clock
+    regs[DS_SECONDS] = TO_BCD((cyg_uint8)second);
+
+    // Send the register set to the hardware
+    DS_PUT(regs);
+
+#ifdef DEBUG
+    // This will cause the test to eventually fail due to these printouts
+    // causing timer interrupts to be lost...
+    diag_printf("Set -------------\n");
+    diag_printf("year %02d\n", year);
+    diag_printf("month %02d\n", month);
+    diag_printf("mday %02d\n", mday);
+    diag_printf("hour %02d\n", hour);
+    diag_printf("minute %02d\n", minute);
+    diag_printf("second %02d\n", second);
+#endif
+}
+
+static inline void
+get_ds_hwclock(cyg_uint32* year, cyg_uint32* month, cyg_uint32* mday,
+               cyg_uint32* hour, cyg_uint32* minute, cyg_uint32* second)
+{
+    cyg_uint8 regs[DS_REGS_SIZE];
+
+    // Fetch the current state
+    DS_GET(regs);
+
+    *year = (cyg_uint32)TO_DEC(regs[DS_YEAR]);
+    // The year field only has the 2 least significant digits :-(
+    if (*year >= 34) {
+        *year += 1900;
+    } else {
+        *year += 2000;
+    }
+    *month = (cyg_uint32)TO_DEC(regs[DS_MONTH]);
+    *mday = (cyg_uint32)TO_DEC(regs[DS_DOM]);
+    *hour = (cyg_uint32)TO_DEC(regs[DS_HOURS] & 0x7F);
+    *minute = (cyg_uint32)TO_DEC(regs[DS_MINUTES]);
+    *second = (cyg_uint32)TO_DEC(regs[DS_SECONDS] & 0x7F);
+
+#ifdef DEBUG
+    // This will cause the test to eventually fail due to these printouts
+    // causing timer interrupts to be lost...
+    diag_printf("year %02d\n", *year);
+    diag_printf("month %02d\n", *month);
+    diag_printf("mday %02d\n", *mday);
+    diag_printf("hour %02d\n", *hour);
+    diag_printf("minute %02d\n", *minute);
+    diag_printf("second %02d\n", *second);
+#endif
+}
+
+//-----------------------------------------------------------------------------
+// Functions required for the hardware-driver API.
+
+// Returns the number of seconds elapsed since 1970-01-01 00:00:00.
+cyg_uint32 
+Cyg_WallClock::get_hw_seconds(void)
+{
+    cyg_uint32 year, month, mday, hour, minute, second;
+
+    get_ds_hwclock(&year, &month, &mday, &hour, &minute, &second);
+    cyg_uint32 now = _simple_mktime(year, month, mday, hour, minute, second);
+    return now;
+}
+
+#ifdef CYGSEM_WALLCLOCK_SET_GET_MODE
+
+// Sets the clock. Argument is seconds elapsed since 1970-01-01 00:00:00.
+void
+Cyg_WallClock::set_hw_seconds( cyg_uint32 secs )
+{
+    cyg_uint32 year, month, mday, hour, minute, second;
+
+    _simple_mkdate(secs, &year, &month, &mday, &hour, &minute, &second);
+    set_ds_hwclock(year, month, mday, hour, minute, second);
+}
+
+#endif
+
+void
+Cyg_WallClock::init_hw_seconds(void)
+{
+#ifdef CYGSEM_WALLCLOCK_SET_GET_MODE
+    init_ds_hwclock();
+#else
+    // This is our base: 1970-01-01 00:00:00
+    // Set the HW clock - if for nothing else, just to be sure it's in a
+    // legal range. Any arbitrary base could be used.
+    // After this the hardware clock is only read.
+    set_ds_hwclock(1970,1,1,0,0,0);
+#endif
+}
+
+//-----------------------------------------------------------------------------
+// End of devs/wallclock/ds1307.inl
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/powerpc/moab/current/ChangeLog
@@ -0,0 +1,40 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/devices_wallclock_moab.inl: 
+	* cdl/moab_wallclock_drivers.cdl: New package - RTC support on 
+	TAMS MOAB (PowerPC 405GPr) board.
+
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+
+
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/powerpc/moab/current/cdl/moab_wallclock_drivers.cdl
@@ -0,0 +1,69 @@
+# ====================================================================
+#
+#      moab_wallclock_drivers.cdl
+#
+#      Wallclock drivers - support for DS1307 RTC on the TAMS MOAB
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      rajt
+# Contributors:   rajt
+# Date:           2001-07-19
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB {
+    display       "TAMS MOAB board RTC Driver"
+    description   "RTC driver for TAMS MOAB."
+
+    parent        CYGPKG_IO_WALLCLOCK
+    active_if     CYGPKG_IO_WALLCLOCK
+    active_if     CYGPKG_HAL_POWERPC_MOAB
+    requires      CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307
+
+    include_dir   cyg/io
+
+    define_proc {
+        puts $::cdl_system_header "/***** MOAB RTC driver proc output start *****/"
+        puts $::cdl_system_header "#define CYGDAT_DEVS_WALLCLOCK_DALLAS_1307_INL <cyg/io/devices_wallclock_moab.inl>"
+        puts $::cdl_system_header "#define CYGDAT_DEVS_WALLCLOCK_MOAB_CFG <pkgconf/devices_wallclock_powerpc_moab.h>"
+        puts $::cdl_system_header "/***** MOAB RTC driver proc output end  *****/"
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/devs/wallclock/powerpc/moab/current/include/devices_wallclock_moab.inl
@@ -0,0 +1,124 @@
+//==========================================================================
+//
+//      devs/wallclock/powerpc/moab/include/devs_wallclock_moab.inl
+//
+//      TAMS MOAB RTC IO definitions
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   rajt
+// Contributors:rajt
+// Date:        2001-07-19
+// Purpose:     MOAB RTC definitions for using DS1307
+//####DESCRIPTIONEND####
+//==========================================================================
+
+#include CYGDAT_DEVS_WALLCLOCK_MOAB_CFG
+
+static __inline__ void
+DS_GET(cyg_uint8 *regs)
+{
+    cyg_uint8 addr, page;
+
+    // Read RTC 
+    addr = 0x00;
+    page = 0xD1;
+    if (!hal_ppc405_i2c_put_bytes(page, &addr, 1)) {
+        diag_printf("%s - Can't select page %x\n", __FUNCTION__, page);
+        return;
+    }
+    if (!hal_ppc405_i2c_get_bytes(page, regs, DS_REGS_SIZE)) {
+        diag_printf("%s - Can't read RTC\n", __FUNCTION__);
+        return;
+    }
+#if 0
+    diag_printf("RTC data - read\n");
+    diag_dump_buf(regs, DS_REGS_SIZE);
+#endif
+
+#ifdef RTC_TEST
+    addr = 0x10;
+    page = 0xD1;
+    if (!hal_ppc405_i2c_put_bytes(page, &addr, 1)) {
+        diag_printf("%s - Can't select page %x\n", __FUNCTION__, page);
+        return;
+    }
+    if (!hal_ppc405_i2c_get_bytes(page, regs, DS_REGS_SIZE)) {
+        diag_printf("%s - Can't read RTC\n", __FUNCTION__);
+        return;
+    }
+    diag_printf("RTC data - test\n");
+    diag_dump_buf(regs, DS_REGS_SIZE);
+#endif
+}
+
+static __inline__ void
+DS_PUT(cyg_uint8 *regs)
+{
+    cyg_uint8 addr_data[DS_REGS_SIZE+1], page;
+    int i;
+
+#if 0
+    diag_printf("RTC data - write\n");
+    diag_dump_buf(regs, DS_REGS_SIZE);
+#endif
+    // Update RTC in one swoop
+    addr_data[0] = 0x00;  // Starting register address
+    for (i = 0;  i < DS_REGS_SIZE;  i++) {
+        addr_data[i+1] = regs[i];
+    }
+    page = 0xD0;
+    if (!hal_ppc405_i2c_put_bytes(page, addr_data, DS_REGS_SIZE+1)) {
+        diag_printf("%s - Can't write registers\n", __FUNCTION__);
+        return;
+    }
+#ifdef RTC_TEST
+    // Test RTC by copying the registers to some of the RAM
+    addr_data[0] = 0x10;  // Starting register address
+    for (i = 0;  i < DS_REGS_SIZE;  i++) {
+        addr_data[i+1] = regs[i];
+    }
+    page = 0xD0;
+    if (!hal_ppc405_i2c_put_bytes(page, addr_data, DS_REGS_SIZE+1)) {
+        diag_printf("%s - Can't write registers\n", __FUNCTION__);
+        return;
+    }
+#endif
+}
+
+// EOF devs_wallclock_moab.inl
--- a/packages/ecos.db
+++ b/packages/ecos.db
@@ -95,6 +95,7 @@ package CYGPKG_IO_SERIAL {
            This package contains drivers for basic I/O services on
            serial devices."
 }
+
 package CYGPKG_IO_PCMCIA {
 	alias 		{ "PCMCIA & Compact Flash support" pcmcia io_pcmcia cf }
 	directory	io/pcmcia
@@ -690,6 +691,17 @@ package CYGPKG_DEVS_FLASH_SYNTH {
     description   "
         FLASH memory device support for Synthetic target"
 }
+
+package CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX {
+	alias 		{ "Support for Toshiba TC58xxx flash memory" flash_toshiba_tc58xxx }
+	directory	devs/flash/toshiba/tc58xxx
+	script		flash_toshiba_tc58xxx.cdl
+	hardware
+        description "
+           This package contains hardware support for Toshiba TC58xxx
+           NAND flash memory devices."
+}
+
 package CYGPKG_DEVS_FLASH_FRV_FRV400 {
         alias           { "Fujitsu FRV400 FLASH memory support" flash_frv400 }
         directory       devs/flash/frv/frv400
@@ -916,6 +928,14 @@ package CYGPKG_IO_SERIAL_POWERPC_QUICC2_
     description       "PowerPC VADS QUICC2/SCC serial device drivers"
 }
 
+package CYGPKG_IO_SERIAL_POWERPC_PPC405 {
+    alias             { "PowerPC PPC405GP serial device drivers" devs_serial_ppc405 }
+    hardware
+    directory	      devs/serial/powerpc/ppc405
+    script	      ser_powerpc_ppc405.cdl	
+    description       "PowerPC PPC405GP serial device drivers"
+}
+
 package CYGPKG_IO_SERIAL_SPARCLITE_SLEB {
     alias             { "SPARClite SLEB serial device drivers"
                         devs_serial_sparclite_sleb sleb_serial_driver }
@@ -1438,6 +1458,14 @@ package CYGPKG_DEVS_ETH_POWERPC_FCC {
         description     "Fast ethernet driver for PowerPC MPCxxx based boards."
 }
 
+package CYGPKG_DEVS_ETH_POWERPC_PPC405 {
+	alias 		{ "PPC405 ethernet driver" ppc405_eth_driver }
+	hardware
+	directory	devs/eth/powerpc/ppc405
+	script		ppc405_eth_drivers.cdl
+        description     "Ethernet driver for PowerPC 405GP based boards."
+}
+
 package CYGPKG_DEVS_ETH_POWERPC_VIPER {
 	alias 		{ "A&M Viper ethernet driver" viper_eth_driver }
 	hardware
@@ -1664,6 +1692,16 @@ package CYGPKG_DEVICES_WALLCLOCK_MPC5xx 
            Motorola mpc5xx CPU's RTC module."
 }
 
+package CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307 {
+	alias		{ "Wallclock driver for Dallas 1307" devices_wallclock_ds1307 device_wallclock_ds1307 }
+	directory	devs/wallclock/dallas/ds1307
+	script          wallclock_ds1307.cdl
+	hardware
+        description "
+           This package provides a driver implementation for 
+           the Dallas 1307 wallclock."
+}
+
 package CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1742 {
 	alias		{ "Wallclock driver for Dallas 1742" devices_wallclock_ds1742 device_wallclock_ds1742 }
 	directory	devs/wallclock/dallas/ds1742
@@ -5024,6 +5062,70 @@ target rattler {
             eCos on an Analogue & Micro Rattler (MPC8250) board."
 }
 
+##-------------------------------------------------------------------------------------------
+## TAMS MOAB (PowerPC 405GPr) packages
+##
+package CYGPKG_HAL_POWERPC_MOAB {
+	alias		{ "TAMS PowerPC 405GP board" hal_powerpc_moab }
+	directory	hal/powerpc/moab
+	script		hal_powerpc_moab.cdl
+	hardware
+        description "
+            The MOAB HAL package provides the support needed to run
+            eCos on a TAMS PowerPC 405GP board."
+}
+
+package CYGPKG_DEVS_FLASH_POWERPC_MOAB {
+	alias 		{ "FLASH memory support for MOAB" flash_moab }
+	directory	devs/flash/powerpc/moab
+	script		flash_moab.cdl
+	hardware
+        description "
+           This package contains hardware support for both the boot FLASH 
+           and NAND (main) memory on the MOAB platform."
+}
+
+package CYGPKG_DEVS_ETH_POWERPC_MOAB {
+        alias           { "TAMS PowerPC 405GP ethernet support" moab_eth_driver }
+        hardware
+        directory       devs/eth/powerpc/moab
+        script          moab_eth_drivers.cdl
+        description     "Ethernet driver specifics for TAMS MOAB (PPC405GP) based boards."
+}
+
+package CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB {
+         alias          { "MOAB RTC device" devs_wallclock_moab_ds1307 moab_rtc }
+         hardware
+         directory      devs/wallclock/powerpc/moab
+         script         moab_wallclock_drivers.cdl
+         description    "
+            RTC driver for MOAB (PowerPC PPC405GPr) using a
+            Dallas DS1307 RTC."
+}
+
+target moab {
+	alias		{ "TAMS PowerPC 405GPr" moab405GPr }
+	packages        { CYGPKG_HAL_POWERPC
+                          CYGPKG_HAL_POWERPC_PPC40x
+                          CYGPKG_HAL_POWERPC_MOAB
+                          CYGPKG_DEVS_FLASH_POWERPC_MOAB
+                          CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX
+                          CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX
+                          CYGPKG_DEVS_ETH_POWERPC_MOAB
+                          CYGPKG_DEVS_ETH_POWERPC_PPC405
+                          CYGPKG_DEVS_ETH_PHY
+                          CYGPKG_IO_PCI
+                          CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307
+                          CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB
+                          CYGPKG_IO_SERIAL_GENERIC_16X5X
+                          CYGPKG_IO_SERIAL_POWERPC_PPC405
+        }
+        description "
+            The moab target provides the packages needed to run
+            eCos on the TAMS MOAB (405GPr) board."
+}
+##-------------------------------------------------------------------------------------------
+
 # --------------------------------------------------------------------------
 
 package CYGPKG_VNC_SERVER {
--- a/packages/hal/powerpc/arch/current/ChangeLog
+++ b/packages/hal/powerpc/arch/current/ChangeLog
@@ -1,3 +1,13 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/vectors.S: Respect initial MMU settings when handling interrupts
+	and exceptions.  Previously, the code would always reenable the MMU,
+	even if it wasn't on when the interrupt occurred.
+
+	* include/hal_io.h: Allow variants to provide I/O definitions
+
+	* cdl/hal_powerpc.cdl: Allow override of CYGHWR_HAL_POWERPC_ENABLE_MMU
+
 2003-08-28  Gary Thomas  <gary@mlbassoc.com>
 
 	* src/redboot_linux_exec.c: New file - architecture level
@@ -51,6 +61,10 @@ 2002-11-14  Gary Thomas  <gthomas@ecosce
 
 	* src/vectors.S: Provide pointer to saved registers on interrupt.
 	This is necessary for profiling support.
+	
+2002-11-20  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/hal_mk_defs.c: Allow platforms to provide their own definitions.
 
 2002-11-13  Gary Thomas  <gthomas@ecoscentric.com>
 
--- a/packages/hal/powerpc/arch/current/cdl/hal_powerpc.cdl
+++ b/packages/hal/powerpc/arch/current/cdl/hal_powerpc.cdl
@@ -154,7 +154,7 @@ cdl_package CYGPKG_HAL_POWERPC {
 
     cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
         display       "Enable MMU"
-        calculated    { !CYGHWR_HAL_POWERPC_DISABLE_MMU }
+        default_value { !CYGHWR_HAL_POWERPC_DISABLE_MMU }
         description   "
             Some platforms do not want the MMU enabled."
     }
--- a/packages/hal/powerpc/arch/current/include/hal_io.h
+++ b/packages/hal/powerpc/arch/current/include/hal_io.h
@@ -12,7 +12,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
-// Copyright (C) 2002 Gary Thomas
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -61,6 +61,9 @@
 //=============================================================================
 
 #include <cyg/infra/cyg_type.h>
+#ifdef CYGBLD_HAL_VAR_IO_H
+#include CYGBLD_HAL_VAR_IO_H
+#endif
 #ifdef CYGBLD_HAL_PLF_IO_H
 #include CYGBLD_HAL_PLF_IO_H
 #endif
--- a/packages/hal/powerpc/arch/current/src/hal_mk_defs.c
+++ b/packages/hal/powerpc/arch/current/src/hal_mk_defs.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -157,6 +158,9 @@ main(void)
 #ifdef CYGARC_VARIANT_DEFS
     CYGARC_VARIANT_DEFS
 #endif
+#ifdef CYGARC_PLATFORM_DEFS
+    CYGARC_PLATFORM_DEFS
+#endif
 
     // Memory layout values (since these aren't "asm"-safe)
 #ifdef CYGMEM_REGION_rom    
--- a/packages/hal/powerpc/arch/current/src/vectors.S
+++ b/packages/hal/powerpc/arch/current/src/vectors.S
@@ -297,7 +297,7 @@ rom_vectors_end:
         # safe to access RAM until after this point.
         bl      hal_hardware_init	# this is platform dependent
         .globl  _hal_hardware_init_done
-_hal_hardware_init_done:                
+_hal_hardware_init_done:
 
 #if !defined(CYG_HAL_STARTUP_ROM) && defined(CYGSEM_HAL_POWERPC_COPY_VECTORS)
         lwi     r3,rom_vectors-4
@@ -474,11 +474,13 @@ cyg_hal_default_exception_vsr:
         stw     r3,CYGARC_PPCREG_WALL_TAIL(sp)
 #endif
 
+#ifdef CYGHWR_HAL_POWERPC_ENABLE_MMU
         # Enable MMU.
         lwi     r3,CYG_MSR
         sync
         mtmsr   r3
         sync
+#endif        
                 
         mfspr   r3,SPRG1                # save original R3
         stw     r3,CYGARC_PPCREG_REGS+3*4(sp)
@@ -621,11 +623,13 @@ cyg_hal_default_interrupt_vsr:
         stw     r3,CYGARC_PPCREG_WALL_TAIL(sp)
 #endif
 
+#ifdef CYGHWR_HAL_POWERPC_ENABLE_MMU
         # Enable MMU.
         lwi     r3,CYG_MSR
         sync
         mtmsr   r3
         sync
+#endif        
 
         mfspr   r3,SPRG1                # save original R3
         stw     r3,CYGARC_PPCREG_REGS+3*4(sp)
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/ChangeLog
@@ -0,0 +1,76 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* support/make_MOAB_flash.c: Tool to create boot flash image
+
+	* sa_tests/tty.c: 
+	* sa_tests/start.S: 
+	* sa_tests/sdram_test.c: 
+	* sa_tests/ppc_ocm.ld: 
+	* sa_tests/ppc_dram.ld: 
+	* sa_tests/ppc.inc: 
+	* sa_tests/flash_test.c: 
+	* sa_tests/Makefile: Stand alone testing support.
+	
+	* misc/redboot_ROMRAM.ecm: 
+	* misc/redboot_ROM.ecm: 
+	* misc/redboot_BOOT.ecm: 
+	* misc/redboot_RAM+FLASH.ecm:
+	* misc/redboot_RAM.ecm: Default RedBoot configurations
+	
+	* src/moab.S: 
+	* src/hal_aux.c: 
+	* src/plf_redboot_linux_exec.c:
+	* include/pkgconf/mlt_powerpc_moab_romram.mlt: 	
+	* include/pkgconf/mlt_powerpc_moab_romram.ldi: 	
+	* include/pkgconf/mlt_powerpc_moab_romram.h: 
+	* include/pkgconf/mlt_powerpc_moab_rom.mlt: 	
+	* include/pkgconf/mlt_powerpc_moab_rom.ldi: 	
+	* include/pkgconf/mlt_powerpc_moab_rom.h: 
+	* include/pkgconf/mlt_powerpc_moab_ram.mlt: 	
+	* include/pkgconf/mlt_powerpc_moab_ram.ldi: 	
+	* include/pkgconf/mlt_powerpc_moab_ram.h: 
+	* include/plf_stub.h: 
+	* include/plf_regs.h: 
+	* include/plf_io.h: 
+	* include/plf_intr.h: 
+	* include/plf_cache.h: 
+	* include/plf.inc: 
+	* include/hal_diag.h: 
+	* cdl/hal_powerpc_moab.cdl: New package - platform support for
+	TAMS MOAB (PowerPC 405GPr) board.
+
+//===========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003, 2002 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//===========================================================================
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/cdl/hal_powerpc_moab.cdl
@@ -0,0 +1,345 @@
+# ====================================================================
+#
+#      hal_powerpc_moab.cdl
+#
+#      PowerPC/MOAB board HAL package configuration data
+#
+# ====================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+# ====================================================================
+######DESCRIPTIONBEGIN####
+#
+# Author(s):      jskov
+# Original data:  hmt
+# Contributors:   gthomas
+# Date:           1999-11-02
+#
+#####DESCRIPTIONEND####
+#
+# ====================================================================
+
+cdl_package CYGPKG_HAL_POWERPC_MOAB {
+    display       "TAMS MOAB (PowerPC 405GPr) board"
+    parent        CYGPKG_HAL_POWERPC
+    requires      CYGPKG_HAL_POWERPC_PPC40x
+    define_header hal_powerpc_moab.h
+    include_dir   cyg/hal
+    description   "
+        The MOAB HAL package provides the support needed to run
+        eCos on a TAMS PowerPC 405GP board."
+
+    compile       hal_aux.c moab.S
+
+    implements    CYGINT_HAL_DEBUG_GDB_STUBS
+    implements    CYGINT_HAL_DEBUG_GDB_STUBS_BREAK
+    implements    CYGINT_HAL_VIRTUAL_VECTOR_SUPPORT
+    requires      CYGSEM_HAL_POWERPC_RESET_USES_JUMP        
+    requires      { CYGHWR_HAL_POWERPC_PPC4XX == "405GP" }
+# work around DCACHE problems - see errata for details, but
+# basically, writethru mode is the only safe way to run this
+    requires      { CYGSEM_HAL_DCACHE_STARTUP_MODE == "WRITETHRU" }
+# having the MMU enabled just seems to cause no end of problems
+    requires      { !CYGHWR_HAL_POWERPC_ENABLE_MMU }
+#
+    requires      { !CYGSEM_REDBOOT_FLASH_CONFIG || 
+                    ((CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA == "EEPROM") &&
+                     (CYGNUM_REDBOOT_FLASH_CONFIG_SIZE == CYGNUM_HAL_EEPROM_SIZE) &&
+                     (CYGNUM_REDBOOT_FLASH_STRING_SIZE == 64) &&
+                     (CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE == 256)) }
+    requires      { !CYGPKG_REDBOOT || CYGBLD_REDBOOT_MAX_MEM_SEGMENTS == 2 }
+
+    define_proc {
+        puts $::cdl_system_header "#define CYGBLD_HAL_TARGET_H   <pkgconf/hal_powerpc_ppc40x.h>"
+        puts $::cdl_system_header "#define CYGBLD_HAL_PLATFORM_H <pkgconf/hal_powerpc_moab.h>"
+        puts $::cdl_system_header "#define CYGBLD_HAL_PLF_IO_H   <cyg/hal/plf_io.h>"
+
+	puts $::cdl_header "#define HAL_PLATFORM_CPU    \"PowerPC 405GPr\""
+        puts $::cdl_header "#define HAL_PLATFORM_BOARD  \"TAMS MOAB\""
+        puts $::cdl_header "#define HAL_PLATFORM_EXTRA  \"\""
+    }
+
+    cdl_component CYG_HAL_STARTUP {
+        display       "Startup type"
+        flavor        data
+        legal_values  {"RAM" "ROM" "ROMRAM"}
+        default_value {"RAM"}
+	no_define
+	define -file system.h CYG_HAL_STARTUP
+        description   "
+           This option is used to control where the application program will
+           run, either from RAM or ROM (flash) memory.  ROM based applications
+           must be self contained, while RAM applications will typically assume
+           the existence of a debug environment, such as GDB stubs."
+    }
+
+    cdl_option CYGHWR_HAL_POWERPC_CPU_SPEED {
+        display          "Development board clock speed (MHz)"
+        flavor           data
+        legal_values     250 333
+        default_value    250
+        description      "
+           MOAB Development Boards have various system clock speeds
+           depending on the processor and oscillator fitted.  Select 
+           the clock speed appropriate for your board so that the system 
+           can set the serial baud rate correctly, amongst other things."
+   }
+
+   cdl_option CYGHWR_HAL_POWERPC_MEM_SPEED {
+        display          "Development board memory bus speed (MHz)"
+        flavor           data
+        legal_values     66
+        default_value    66
+        description      "
+           MOAB Development Boards have various system clock speeds
+           depending on the processor and oscillator fitted."
+   }
+
+    cdl_component CYGNUM_HAL_EEPROM_SIZE {
+        display       "Size of EEPROM device"
+        flavor        data
+        legal_values  { 1024 2048 4192 }
+        default_value { 2048 }
+        description   "
+           This option is used to control where the application program will
+           run, either from RAM or ROM (flash) memory.  ROM based applications
+           must be self contained, while RAM applications will typically assume
+           the existence of a debug environment, such as GDB stubs."
+    }
+    
+    cdl_component CYGBLD_GLOBAL_OPTIONS {
+        display "Global build options"
+        flavor  none
+        description   "
+	    Global build options including control over
+	    compiler flags, linker flags and choice of toolchain."
+
+
+        parent  CYGPKG_NONE
+
+        cdl_option CYGBLD_GLOBAL_COMMAND_PREFIX {
+            display "Global command prefix"
+            flavor  data
+            no_define
+            default_value { "powerpc-eabi" }
+            description "
+                This option specifies the command prefix used when
+                invoking the build tools."
+        }
+
+        cdl_option CYGBLD_GLOBAL_CFLAGS {
+            display "Global compiler flags"
+            flavor  data
+            no_define
+            default_value { "-msoft-float -mcpu=405 -Wall -Wpointer-arith -Wstrict-prototypes -Winline -Wundef -Woverloaded-virtual -g -O2 -ffunction-sections -fdata-sections -fno-rtti -fno-exceptions -fvtable-gc -finit-priority" }
+            description   "
+                This option controls the global compiler flags which
+                are used to compile all packages by
+                default. Individual packages may define
+                options which override these global flags."
+        }
+
+        cdl_option CYGBLD_GLOBAL_LDFLAGS {
+            display "Global linker flags"
+            flavor  data
+            no_define
+            default_value { "-msoft-float -mcpu=405 -g -nostdlib -Wl,--gc-sections -Wl,-static" }
+            description   "
+                This option controls the global linker flags. Individual
+                packages may define options which override these global flags."
+        }
+
+        cdl_option CYGBLD_BUILD_GDB_STUBS {
+            display "Build GDB stub ROM image"
+            default_value 0
+            requires { CYG_HAL_STARTUP == "ROM" }
+            requires CYGSEM_HAL_ROM_MONITOR
+            requires CYGBLD_BUILD_COMMON_GDB_STUBS
+            requires CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
+            requires CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT
+            requires CYGDBG_HAL_DEBUG_GDB_THREAD_SUPPORT
+            requires ! CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT
+            requires ! CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM
+            no_define
+            description "
+                This option enables the building of the GDB stubs for the
+                board. The common HAL controls takes care of most of the
+                build process, but the platform CDL takes care of creating
+                an S-Record data file suitable for programming using
+                the board's EPPC-Bug firmware monitor."
+
+            make -priority 320 {
+                <PREFIX>/bin/gdb_module.bin : <PREFIX>/bin/gdb_module.img
+                $(OBJCOPY) -O srec --change-address=0x02000000 $< $(@:.bin=.srec)
+                $(OBJCOPY) -O binary $< $@
+            }
+        }
+    }
+
+    cdl_component CYGPKG_HAL_POWERPC_MOAB_OPTIONS {
+        display "MOAB build options"
+        flavor  none
+        description   "
+	    Package specific build options including control over
+	    compiler flags used only in building this package,
+	    and details of which tests are built."
+
+
+        cdl_option CYGPKG_HAL_POWERPC_MOAB_CFLAGS_ADD {
+            display "Additional compiler flags"
+            flavor  data
+            no_define
+            default_value { "" }
+            description   "
+                This option modifies the set of compiler flags for
+                building the MOAB HAL. These flags are used in addition
+                to the set of global flags."
+        }
+
+        cdl_option CYGPKG_HAL_POWERPC_MOAB_CFLAGS_REMOVE {
+            display "Suppressed compiler flags"
+            flavor  data
+            no_define
+            default_value { "" }
+            description   "
+                This option modifies the set of compiler flags for
+                building the MOAB HAL. These flags are removed from
+                the set of global flags if present."
+        }
+
+        cdl_option CYGPKG_HAL_POWERPC_MOAB_TESTS {
+            display "MOAB tests"
+            flavor  data
+            no_define
+            calculated { "tests/moabtime" }
+            description   "
+                This option specifies the set of tests for the MOAB HAL."
+        }
+    }
+
+    cdl_component CYGHWR_MEMORY_LAYOUT {
+        display "Memory layout"
+        flavor data
+        no_define
+        calculated { CYG_HAL_STARTUP == "RAM" ? "powerpc_moab_ram" : \
+                     CYG_HAL_STARTUP == "ROMRAM" ? "powerpc_moab_romram" : \
+                                                "powerpc_moab_rom" }
+
+        cdl_option CYGHWR_MEMORY_LAYOUT_LDI {
+            display "Memory layout linker script fragment"
+            flavor data
+            no_define
+            define -file system.h CYGHWR_MEMORY_LAYOUT_LDI
+            calculated { CYG_HAL_STARTUP == "RAM" ? "<pkgconf/mlt_powerpc_moab_ram.ldi>" : \
+                         CYG_HAL_STARTUP == "ROMRAM" ? "<pkgconf/mlt_powerpc_moab_romram.ldi>" : \
+                                                    "<pkgconf/mlt_powerpc_moab_rom.ldi>" }
+        }
+
+        cdl_option CYGHWR_MEMORY_LAYOUT_H {
+            display "Memory layout header file"
+            flavor data
+            no_define
+            define -file system.h CYGHWR_MEMORY_LAYOUT_H
+            calculated { CYG_HAL_STARTUP == "RAM" ? "<pkgconf/mlt_powerpc_moab_ram.h>" : \
+                         CYG_HAL_STARTUP == "ROMRAM" ? "<pkgconf/mlt_powerpc_moab_romram.h>" : \
+                                                    "<pkgconf/mlt_powerpc_moab_rom.h>" }
+        }
+    }
+
+    cdl_option CYGSEM_HAL_ROM_MONITOR {
+        display       "Behave as a ROM monitor"
+        flavor        bool
+        default_value 0
+        parent        CYGPKG_HAL_ROM_MONITOR
+        requires      { CYG_HAL_STARTUP == "ROM" || CYG_HAL_STARTUP == "ROMRAM" }
+        description   "
+            Enable this option if this program is to be used as a ROM monitor,
+            i.e. applications will be loaded into RAM on the board, and this
+            ROM monitor may process exceptions or interrupts generated from the
+            application. This enables features such as utilizing a separate
+            interrupt stack when exceptions are generated."
+    }
+
+    cdl_component CYGPKG_REDBOOT_HAL_OPTIONS {
+        display       "Redboot HAL options"
+        flavor        none
+        no_define
+        parent        CYGPKG_REDBOOT
+        active_if     CYGPKG_REDBOOT
+        description   "
+            This option lists the target's requirements for a valid Redboot
+            configuration."
+
+        cdl_option CYGSEM_REDBOOT_PLF_LINUX_BOOT {
+            active_if      CYGBLD_BUILD_REDBOOT_WITH_EXEC
+            display        "Support booting Linux via RedBoot"
+            flavor         bool
+            default_value  1
+            description    "
+               This option enables RedBoot to support booting of a Linux kernel."
+
+            compile plf_redboot_linux_exec.c
+        }
+
+        cdl_component CYGBLD_BUILD_REDBOOT_OBJS {
+            display       "Build Redboot image(s)"
+            active_if     CYGBLD_BUILD_REDBOOT
+            default_value 1
+            no_define
+            description "This option enables the conversion of the Redboot ELF
+                         image various formats which simplify further manipulatations.
+                         The most basic of these forms is Motorola S-records, which
+                         are simpler and more reliable than binary formats when used
+                         for serial download."
+
+            make -priority 325 {
+                <PREFIX>/bin/redboot.srec : <PREFIX>/bin/redboot.elf
+                $(OBJCOPY) -O srec $< $(@:.bin=.srec)
+            }
+
+            cdl_option CYGBLD_BUILD_REDBOOT_BIN {
+                display       "Build RedBoot ROM/FLASH binary image"
+                default_value { CYG_HAL_STARTUP != "RAM" }
+                description "This option enables the conversion of the Redboot ELF
+                             image to a binary image suitable for ROM/FLASH programming."
+                make -priority 324 {
+                    <PREFIX>/bin/redboot.bin : <PREFIX>/bin/redboot.elf
+                    $(OBJCOPY) -O binary $< /tmp/__redboot.bin
+                    make_MOAB_flash /tmp/__redboot.bin $@
+                    rm -f /tmp/__redboot.bin
+                }
+            }
+        }
+    }
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/hal_diag.h
@@ -0,0 +1,69 @@
+#ifndef CYGONCE_HAL_HAL_DIAG_H
+#define CYGONCE_HAL_HAL_DIAG_H
+
+//=============================================================================
+//
+//      hal_diag.h
+//
+//      HAL Support for Kernel Diagnostic Routines
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   nickg
+// Contributors:nickg
+// Date:        1998-03-02
+// Purpose:     HAL Support for Kernel Diagnostic Routines
+// Description: Diagnostic routines for use during kernel development.
+// Usage:       #include <cyg/hal/hal_diag.h>
+//
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+#include <pkgconf/hal.h>
+
+#include <cyg/infra/cyg_type.h>
+#include <cyg/hal/hal_if.h>
+
+#define HAL_DIAG_INIT() hal_if_diag_init()
+#define HAL_DIAG_WRITE_CHAR(_c_) hal_if_diag_write_char(_c_)
+#define HAL_DIAG_READ_CHAR(_c_) hal_if_diag_read_char(&_c_)
+
+//-----------------------------------------------------------------------------
+// end of hal_diag.h
+#endif // CYGONCE_HAL_HAL_DIAG_H
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.h
@@ -0,0 +1,37 @@
+// eCos memory layout - Thu May 30 10:27:39 2002
+
+// This is a generated file - do not edit
+
+#ifndef __ASSEMBLER__
+#include <cyg/infra/cyg_type.h>
+#include <stddef.h>
+
+#endif
+#define CYGMEM_REGION_ram (0)
+#define CYGMEM_REGION_ram_SIZE (0x4000000)
+#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_vectors) [];
+#endif
+#define CYGMEM_SECTION_reserved_vectors (CYG_LABEL_NAME (__reserved_vectors))
+#define CYGMEM_SECTION_reserved_vectors_SIZE (0x3000)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_vsr_table) [];
+#endif
+#define CYGMEM_SECTION_reserved_vsr_table (CYG_LABEL_NAME (__reserved_vsr_table))
+#define CYGMEM_SECTION_reserved_vsr_table_SIZE (0x200)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_virtual_table) [];
+#endif
+#define CYGMEM_SECTION_reserved_virtual_table (CYG_LABEL_NAME (__reserved_virtual_table))
+#define CYGMEM_SECTION_reserved_virtual_table_SIZE (0x100)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_for_rom) [];
+#endif
+#define CYGMEM_SECTION_reserved_for_rom (CYG_LABEL_NAME (__reserved_for_rom))
+#define CYGMEM_SECTION_reserved_for_rom_SIZE (0x7cd00)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__heap1) [];
+#endif
+#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1))
+#define CYGMEM_SECTION_heap1_SIZE (0x4000000 - (size_t) CYG_LABEL_NAME (__heap1))
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.ldi
@@ -0,0 +1,31 @@
+// eCos memory layout - Thu May 30 10:27:39 2002
+
+// This is a generated file - do not edit
+
+#include <cyg/infra/cyg_type.inc>
+
+MEMORY
+{
+    ram : ORIGIN = 0, LENGTH = 0x4000000
+}
+
+SECTIONS
+{
+    SECTIONS_BEGIN
+    CYG_LABEL_DEFN(__reserved_vectors) = 0; . = CYG_LABEL_DEFN(__reserved_vectors) + 0x3000;
+    CYG_LABEL_DEFN(__reserved_vsr_table) = ALIGN (0x10); . = CYG_LABEL_DEFN(__reserved_vsr_table) + 0x200;
+    CYG_LABEL_DEFN(__reserved_virtual_table) = ALIGN (0x10); . = CYG_LABEL_DEFN(__reserved_virtual_table) + 0x100;
+    CYG_LABEL_DEFN(__reserved_for_rom) = ALIGN (0x10); . = CYG_LABEL_DEFN(__reserved_for_rom) + 0x7cd00;
+    SECTION_vectors (ram, ALIGN (0x10), LMA_EQ_VMA)
+    SECTION_text (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_fini (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_rodata1 (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_rodata (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_fixup (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_gcc_except_table (ram, ALIGN (0x1), LMA_EQ_VMA)
+    SECTION_data (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_sbss (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_bss (ram, ALIGN (0x10), LMA_EQ_VMA)
+    CYG_LABEL_DEFN(__heap1) = ALIGN (0x8);
+    SECTIONS_END
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_ram.mlt
@@ -0,0 +1,17 @@
+version 0
+region ram 0 4000000 0 !
+section reserved_vectors 3000 1 0 0 1 1 1 1 0 0 reserved_vsr_table reserved_vsr_table !
+section reserved_vsr_table 200 10 0 0 0 1 0 1 reserved_virtual_table reserved_virtual_table !
+section reserved_virtual_table 100 10 0 0 0 1 0 1 reserved_for_rom reserved_for_rom !
+section reserved_for_rom 3cd00 10 0 0 0 1 0 1 vectors vectors !
+section vectors 0 10 0 1 0 1 0 1 text text !
+section text 0 4 0 1 0 1 0 1 fini fini !
+section fini 0 4 0 1 0 1 0 1 rodata1 rodata1 !
+section rodata1 0 8 0 1 0 1 0 1 rodata rodata !
+section rodata 0 8 0 1 0 1 0 1 fixup fixup !
+section fixup 0 4 0 1 0 1 0 1 gcc_except_table gcc_except_table !
+section gcc_except_table 0 1 0 1 0 1 0 1 data data !
+section data 0 8 0 1 0 1 0 1 sbss sbss !
+section sbss 0 4 0 1 0 1 0 1 bss bss !
+section bss 0 10 0 1 0 1 0 1 heap1 heap1 !
+section heap1 0 8 0 0 0 0 0 0 !
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.h
@@ -0,0 +1,35 @@
+// eCos memory layout - Thu May 30 10:21:41 2002
+
+// This is a generated file - do not edit
+
+#ifndef __ASSEMBLER__
+#include <cyg/infra/cyg_type.h>
+#include <stddef.h>
+
+#endif
+#define CYGMEM_REGION_ram (0)
+#define CYGMEM_REGION_ram_SIZE (0x4000000)
+#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W)
+#define CYGMEM_REGION_rom (0xffe00000)
+#define CYGMEM_REGION_rom_SIZE (0x200000)
+#define CYGMEM_REGION_rom_ATTR (CYGMEM_REGION_ATTR_R)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_vectors) [];
+#endif
+#define CYGMEM_SECTION_reserved_vectors (CYG_LABEL_NAME (__reserved_vectors))
+#define CYGMEM_SECTION_reserved_vectors_SIZE (0x3000)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_vsr_table) [];
+#endif
+#define CYGMEM_SECTION_reserved_vsr_table (CYG_LABEL_NAME (__reserved_vsr_table))
+#define CYGMEM_SECTION_reserved_vsr_table_SIZE (0x200)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__reserved_virtual_table) [];
+#endif
+#define CYGMEM_SECTION_reserved_virtual_table (CYG_LABEL_NAME (__reserved_virtual_table))
+#define CYGMEM_SECTION_reserved_virtual_table_SIZE (0x100)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__heap1) [];
+#endif
+#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1))
+#define CYGMEM_SECTION_heap1_SIZE (0x4000000 - (size_t) CYG_LABEL_NAME (__heap1))
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.ldi
@@ -0,0 +1,34 @@
+// eCos memory layout - Thu May 30 10:21:41 2002
+
+// This is a generated file - do not edit
+
+#include <cyg/infra/cyg_type.inc>
+
+MEMORY
+{
+    ram : ORIGIN = 0, LENGTH = 0x4000000
+    rom : ORIGIN = 0xfff80000, LENGTH = 0x80000
+}
+
+SECTIONS
+{
+    SECTIONS_BEGIN
+    SECTION_vectors (rom, 0xfff80000, LMA_EQ_VMA)
+    SECTION_text (rom, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_fini (rom, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_rodata1 (rom, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_rodata (rom, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_fixup (rom, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_gcc_except_table (rom, ALIGN (0x1), LMA_EQ_VMA)
+
+    .reset_vector 0xFFFFFFFC : LMA_EQ_VMA { . = .; KEEP(*(.reset_vector)) } >rom
+
+    CYG_LABEL_DEFN(__reserved_vectors) = 0; . = CYG_LABEL_DEFN(__reserved_vectors) + 0x3000;
+    CYG_LABEL_DEFN(__reserved_vsr_table) = ALIGN (0x1); . = CYG_LABEL_DEFN(__reserved_vsr_table) + 0x200;
+    CYG_LABEL_DEFN(__reserved_virtual_table) = ALIGN (0x1); . = CYG_LABEL_DEFN(__reserved_virtual_table) + 0x100;
+    SECTION_data (ram, ALIGN (0x10), FOLLOWING (.gcc_except_table))
+    SECTION_sbss (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_bss (ram, ALIGN (0x10), LMA_EQ_VMA)
+    CYG_LABEL_DEFN(__heap1) = ALIGN (0x8);
+    SECTIONS_END
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_rom.mlt
@@ -0,0 +1,17 @@
+version 0
+region ram 0 4000000 0 !
+region rom fff80000 80000 1 !
+section reserved_vectors 3000 1 0 0 1 1 1 1 0 0 reserved_vsr_table reserved_vsr_table !
+section reserved_vsr_table 200 1 0 0 0 1 0 1 reserved_virtual_table reserved_virtual_table !
+section reserved_virtual_table 100 1 0 0 0 1 0 0 data !
+section data 0 10 1 1 0 1 0 0 sbss !
+section sbss 0 4 0 1 0 1 0 1 bss bss !
+section bss 0 10 0 1 0 1 0 1 heap1 heap1 !
+section heap1 0 8 0 0 0 0 0 0 !
+section vectors 0 1 0 1 1 1 1 1 fff80000 fff80000 text text !
+section text 0 4 0 1 0 1 0 1 fini fini !
+section fini 0 4 0 1 0 1 0 1 rodata1 rodata1 !
+section rodata1 0 8 0 1 0 1 0 1 rodata rodata !
+section rodata 0 8 0 1 0 1 0 1 fixup fixup !
+section fixup 0 4 0 1 0 1 0 1 gcc_except_table gcc_except_table !
+section gcc_except_table 0 1 0 1 0 0 0 1 data !
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.h
@@ -0,0 +1,19 @@
+// eCos memory layout - Thu May 30 10:05:45 2002
+
+// This is a generated file - do not edit
+
+#ifndef __ASSEMBLER__
+#include <cyg/infra/cyg_type.h>
+#include <stddef.h>
+
+#endif
+#define CYGMEM_REGION_ram (0)
+#define CYGMEM_REGION_ram_SIZE (0x2000000)
+#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W)
+#define CYGMEM_REGION_rom (0xfff80000)
+#define CYGMEM_REGION_rom_SIZE (0x80000)
+#ifndef __ASSEMBLER__
+extern char CYG_LABEL_NAME (__heap1) [];
+#endif
+#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1))
+#define CYGMEM_SECTION_heap1_SIZE (0x2000000 - (size_t) CYG_LABEL_NAME (__heap1))
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.ldi
@@ -0,0 +1,27 @@
+// eCos memory layout - Thu May 30 10:05:45 2002
+
+// This is a generated file - do not edit
+
+#include <cyg/infra/cyg_type.inc>
+
+MEMORY
+{
+    ram : ORIGIN = 0, LENGTH = 0x4000000
+}
+
+SECTIONS
+{
+    SECTIONS_BEGIN
+    SECTION_vectors (ram, 0, LMA_EQ_VMA)
+    SECTION_text (ram, 0x3400, LMA_EQ_VMA)
+    SECTION_fini (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_rodata1 (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_rodata (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_fixup (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_gcc_except_table (ram, ALIGN (0x1), LMA_EQ_VMA)
+    SECTION_data (ram, ALIGN (0x8), LMA_EQ_VMA)
+    SECTION_sbss (ram, ALIGN (0x4), LMA_EQ_VMA)
+    SECTION_bss (ram, ALIGN (0x10), LMA_EQ_VMA)
+    CYG_LABEL_DEFN(__heap1) = ALIGN (0x8);
+    SECTIONS_END
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/pkgconf/mlt_powerpc_moab_romram.mlt
@@ -0,0 +1,13 @@
+version 0
+region ram 0 4000000 0 !
+section vectors 0 1 0 1 1 0 1 0 0 0 !
+section text 0 1 0 1 1 1 1 1 3400 3400 fini fini !
+section fini 0 4 0 1 0 1 0 1 rodata1 rodata1 !
+section rodata1 0 8 0 1 0 1 0 1 rodata rodata !
+section rodata 0 8 0 1 0 1 0 1 fixup fixup !
+section fixup 0 4 0 1 0 1 0 1 gcc_except_table gcc_except_table !
+section gcc_except_table 0 1 0 1 0 1 0 1 data data !
+section data 0 8 0 1 0 1 0 1 sbss sbss !
+section sbss 0 4 0 1 0 1 0 1 bss bss !
+section bss 0 10 0 1 0 1 0 1 heap1 heap1 !
+section heap1 0 8 0 0 0 0 0 0 !
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf.inc
@@ -0,0 +1,62 @@
+#ifndef CYGONCE_HAL_PLF_INC
+#define CYGONCE_HAL_PLF_INC
+##=============================================================================
+##
+##	plf.inc
+##
+##	PPC40x family assembler header file
+##
+##=============================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+##=============================================================================
+#######DESCRIPTIONBEGIN####
+##
+## Author(s): 	jskov
+## Contributors:jskov, gthomas
+## Date:	2000-08-27
+## Purpose:	PPC40x family definitions.
+## Description:	This file contains various definitions and macros that are
+##              useful for writing assembly code for the PPC40x CPU family.
+## Usage:
+##		#include <cyg/hal/plf.inc>
+##		...
+##		
+##
+######DESCRIPTIONEND####
+##
+##=============================================================================
+
+
+#endif // CYGONCE_HAL_PLF_INC
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf_cache.h
@@ -0,0 +1,78 @@
+#ifndef CYGONCE_PLF_CACHE_H
+#define CYGONCE_PLF_CACHE_H
+
+//=============================================================================
+//
+//      plf_cache.h
+//
+//      Platform HAL cache details
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   jskov
+// Contributors:jskov
+// Date:        2000-01-26
+// Purpose:     Platform cache control API
+// Description: The macros defined here provide the platform specific
+//              cache control operations / behavior.
+// Usage:       Is included via the architecture cache header:
+//              #include <cyg/hal/hal_cache.h>
+//
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+//---------------------------------------------------------------------------
+// Initial cache enabling - controlled by common CDL
+
+//-----------------------------------------------------------------------------
+// FIXME: This definition forces the IO flash driver to use a
+// known-good procedure for fiddling flash before calling flash device
+// driver functions. The procedure breaks on other platform/driver
+// combinations though so is depricated. Hence this definition.
+//
+// If you work on this target, please try to remove this definition
+// and verify that the flash driver still works (both from RAM and
+// flash). If it does, remove the definition and this comment for good
+// [and the old macro definition if this happens to be the last client
+// of that code].
+#define HAL_FLASH_CACHES_OLD_MACROS
+
+//-----------------------------------------------------------------------------
+#endif // ifndef CYGONCE_PLF_CACHE_H
+// End of plf_cache.h
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf_intr.h
@@ -0,0 +1,77 @@
+#ifndef CYGONCE_HAL_PLF_INTR_H
+#define CYGONCE_HAL_PLF_INTR_H
+
+//==========================================================================
+//
+//      plf_intr.h
+//
+//      MOAB platform specific interrupt definitions
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    jskov
+// Contributors: jskov, gthomas
+// Date:         2000-06-13
+// Purpose:      Define platform specific interrupt support
+//              
+// Usage:
+//              #include <cyg/hal/plf_intr.h>
+//              ...
+//              
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <pkgconf/hal.h>
+
+#include <cyg/infra/cyg_type.h>
+
+//--------------------------------------------------------------------------
+// Control-C support.
+
+//----------------------------------------------------------------------------
+// Reset.
+
+externC void _moab_reset(void);
+#define HAL_PLATFORM_RESET() _moab_reset()
+#define HAL_PLATFORM_RESET_ENTRY 0xFFF80100
+
+//--------------------------------------------------------------------------
+#endif // ifndef CYGONCE_HAL_PLF_INTR_H
+// End of plf_intr.h
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf_io.h
@@ -0,0 +1,88 @@
+#ifndef CYGONCE_PLF_IO_H
+#define CYGONCE_PLF_IO_H
+
+//=============================================================================
+//
+//      plf_io.h
+//
+//      Platform specific IO support
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    hmt, jskov 
+// Contributors: hmt, jskov, gthomas
+// Date:         2002-07-23
+// Purpose:      TAMS MOAB (PowerPC 405GPr) PCI IO support macros
+// Description: 
+// Usage:        #include <cyg/hal/plf_io.h>
+//
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+//-----------------------------------------------------------------------------
+//
+// PCI support
+//
+#define CYGARC_PHYSICAL_ADDRESS(x) ((unsigned long)(x) & 0x7FFFFFFF)
+
+// Restrict device [slot] space
+#define CYG_PCI_MAX_BUS                       1  // Only one BUS
+#define CYG_PCI_MIN_DEV                       1  // Slots start at 11
+#define CYG_PCI_MAX_DEV                      21  // ... and end at 31
+
+//-----------------------------------------------------------------------------
+// Resources
+
+// Map PCI device resources starting from these addresses in PCI space.
+#define HAL_PCI_ALLOC_BASE_MEMORY                 0x00000000
+#define HAL_PCI_ALLOC_BASE_IO                     0x00000000
+
+// This is where the PCI spaces are mapped in the CPU's address space.
+#define HAL_PCI_PHYSICAL_MEMORY_BASE              0xA0000000
+#define HAL_PCI_PHYSICAL_IO_BASE                  0xE8800000
+
+#if 1 // This is an old-school idea about how to handle PCI devices
+// These seem to be defined multiple ways?
+#define CYGMEM_SECTION_pci_window                 0x03F00000
+#define CYGMEM_SECTION_pci_window_SIZE            0x00100000
+#endif
+
+//-----------------------------------------------------------------------------
+// end of plf_io.h
+#endif // CYGONCE_PLF_IO_H
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf_regs.h
@@ -0,0 +1,70 @@
+#ifndef CYGONCE_HAL_PLF_REGS_H
+#define CYGONCE_HAL_PLF_REGS_H
+
+//==========================================================================
+//
+//      plf_regs.h
+//
+//      TAMS MOAB PowerPC 405GP platform CPU definitions
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    Gary Thomas <gary@mlbassoc.com>
+// Contributors: 
+// Date:         2003-09-02
+// Purpose:      
+// Description:  Possibly override any platform assumptions
+//
+// Usage:        Included via the variant+architecture register headers:
+//               ...
+//              
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+// Special memory regions
+#define _MOAB_NAND  0xC0000000  // Mapped window to main NAND device
+#define _MOAB_OCM   0xD0000000  // Mapped window to on-chip memory (4KB only)
+
+// GPIO Layout
+#define _MOAB_CLE   0x00010000  // GPIO 15 - asserts CLE to NAND device
+#define _MOAB_ALE   0x00020000  // GPIO 14 - asserts ALE to NAND device
+#define _MOAB_CE    0x00004000  // GPIO 17 - asserts CE to NAND device (active low)
+#define _MOAB_RDY   0x00000200  // GPIO 22 - NAND RDY
+
+#endif // CYGONCE_HAL_PLF_REGS_H
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/include/plf_stub.h
@@ -0,0 +1,88 @@
+#ifndef CYGONCE_HAL_PLF_STUB_H
+#define CYGONCE_HAL_PLF_STUB_H
+
+//=============================================================================
+//
+//      plf_stub.h
+//
+//      Platform header for GDB stub support.
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   jskov
+// Contributors:jskov, gthomas
+// Date:        1999-02-12
+// Purpose:     Platform HAL stub support for Cogent CSB272 PowerPC/405GP board.
+// Usage:       #include <cyg/hal/plf_stub.h>
+//              
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+#include <pkgconf/hal.h>
+
+#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
+
+#include <cyg/infra/cyg_type.h>         // CYG_UNUSED_PARAM
+
+#include <cyg/hal/ppc_stub.h>           // architecture stub support
+
+//----------------------------------------------------------------------------
+// Define some platform specific communication details. This is mostly
+// handled by hal_if now, but we need to make sure the comms tables are
+// properly initialized.
+
+externC void cyg_hal_plf_comms_init(void);
+
+#define HAL_STUB_PLATFORM_INIT_SERIAL()       cyg_hal_plf_comms_init()
+
+#define HAL_STUB_PLATFORM_SET_BAUD_RATE(baud) CYG_UNUSED_PARAM(int, (baud))
+#define HAL_STUB_PLATFORM_INIT_BREAK_IRQ()    CYG_EMPTY_STATEMENT
+#define HAL_STUB_PLATFORM_INTERRUPTIBLE       0
+
+//----------------------------------------------------------------------------
+// Stub initializer.
+#ifdef CYG_HAL_STARTUP_ROM
+# define HAL_STUB_PLATFORM_INIT()
+// to distinguish eCos stub ROM ready state from either RedBoot or app.
+#endif
+
+#endif // ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
+//-----------------------------------------------------------------------------
+#endif // CYGONCE_HAL_PLF_STUB_H
+// End of plf_stub.h
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/misc/redboot_BOOT.ecm
@@ -0,0 +1,176 @@
+cdl_savefile_version 1;
+cdl_savefile_command cdl_savefile_version {};
+cdl_savefile_command cdl_savefile_command {};
+cdl_savefile_command cdl_configuration { description hardware template package };
+cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value };
+
+cdl_configuration eCos {
+    description "" ;
+    hardware    moab ;
+    template    redboot ;
+    package -hardware CYGPKG_HAL_POWERPC current ;
+    package -hardware CYGPKG_HAL_POWERPC_PPC40x current ;
+    package -hardware CYGPKG_HAL_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX current ;
+    package -hardware CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_PPC405 current ;
+    package -hardware CYGPKG_DEVS_ETH_PHY current ;
+    package -hardware CYGPKG_IO_PCI current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307 current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB current ;
+    package -hardware CYGPKG_IO_SERIAL_GENERIC_16X5X current ;
+    package -hardware CYGPKG_IO_SERIAL_POWERPC_PPC405 current ;
+    package -template CYGPKG_HAL current ;
+    package -template CYGPKG_INFRA current ;
+    package -template CYGPKG_REDBOOT current ;
+    package -template CYGPKG_ISOINFRA current ;
+    package -template CYGPKG_LIBC_STRING current ;
+    package -template CYGPKG_NS_DNS current ;
+    package -template CYGPKG_CRC current ;
+    package CYGPKG_IO_ETH_DRIVERS current ;
+    package CYGPKG_IO_WALLCLOCK current ;
+    package CYGPKG_IO_FLASH current ;
+};
+
+cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS {
+    inferred_value 0
+};
+
+cdl_option CYGNUM_IO_ETH_DRIVERS_NUM_PKT {
+    user_value 32
+};
+
+cdl_option CYGSEM_IO_ETH_DRIVERS_WARN {
+    user_value 0
+};
+
+cdl_option CYGHWR_DEVS_ETH_PHY_DP83847 {
+    inferred_value 1
+};
+
+cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE {
+    user_value 4096
+};
+
+cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT {
+    user_value 0
+};
+
+cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_HAL_DCACHE_STARTUP_MODE {
+    inferred_value WRITETHRU
+};
+
+cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_ROM_MONITOR {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_POWERPC_RESET_USES_JUMP {
+    inferred_value 1
+};
+
+cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
+    inferred_value 0
+};
+
+cdl_component CYG_HAL_STARTUP {
+    user_value ROMRAM
+};
+
+cdl_component CYGBLD_BUILD_REDBOOT {
+    user_value 1
+};
+
+cdl_option CYGBLD_REDBOOT_MAX_MEM_SEGMENTS {
+    inferred_value 2
+};
+
+cdl_option CYGNUM_REDBOOT_NETWORKING_MAX_PKTBUF {
+    user_value 8
+};
+
+cdl_option CYGSEM_REDBOOT_PLF_STARTUP {
+    user_value 1
+};
+
+cdl_option CYGBLD_REDBOOT_MIN_IMAGE_SIZE {
+    user_value 0x00080000
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
+    inferred_value 2048
+};
+
+cdl_option CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA {
+    inferred_value EEPROM
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
+    inferred_value 64
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
+    inferred_value 256
+};
+
+cdl_option CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK {
+    inferred_value 0
+};
+
+cdl_option CYGBLD_ISO_STRTOK_R_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/bsdstring.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_DNS_HEADER {
+    inferred_value 1 <cyg/ns/dns/dns.h>
+};
+
+cdl_option CYGPKG_NS_DNS_BUILD {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_IO_FLASH_READ_INDIRECT {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_IO_FLASH_CHATTER {
+    user_value 0
+};
+
+cdl_option CYGSEM_IO_FLASH_VERIFY_PROGRAM {
+    inferred_value 0
+};
+
+cdl_component CYGSEM_DEVS_FLASH_POWERPC_MOAB_MAIN {
+    user_value 1
+};
+
+
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/misc/redboot_RAM+FLASH.ecm
@@ -0,0 +1,125 @@
+cdl_savefile_version 1;
+cdl_savefile_command cdl_savefile_version {};
+cdl_savefile_command cdl_savefile_command {};
+cdl_savefile_command cdl_configuration { description hardware template package };
+cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value };
+
+cdl_configuration eCos {
+    description "" ;
+    hardware    moab ;
+    template    redboot ;
+    package -hardware CYGPKG_HAL_POWERPC current ;
+    package -hardware CYGPKG_HAL_POWERPC_PPC40x current ;
+    package -hardware CYGPKG_HAL_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_PPC405 current ;
+    package -hardware CYGPKG_DEVS_ETH_PHY current ;
+    package -template CYGPKG_HAL current ;
+    package -template CYGPKG_INFRA current ;
+    package -template CYGPKG_REDBOOT current ;
+    package -template CYGPKG_ISOINFRA current ;
+    package -template CYGPKG_LIBC_STRING current ;
+    package -template CYGPKG_NS_DNS current ;
+    package -template CYGPKG_CRC current ;
+    package CYGPKG_IO_FLASH current ;
+    package CYGPKG_IO_ETH_DRIVERS current ;
+};
+
+cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS {
+    inferred_value 0
+};
+
+cdl_option CYGHWR_DEVS_ETH_PHY_DP83847 {
+    inferred_value 1
+};
+
+cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE {
+    user_value 4096
+};
+
+cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT {
+    user_value 0
+};
+
+cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_HAL_DCACHE_STARTUP_MODE {
+    inferred_value WRITETHRU
+};
+
+cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_POWERPC_RESET_USES_JUMP {
+    inferred_value 1
+};
+
+cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
+    user_value 0
+};
+
+cdl_component CYGBLD_BUILD_REDBOOT {
+    user_value 1
+};
+
+cdl_component CYGSEM_REDBOOT_FLASH_CONFIG {
+    inferred_value 0
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
+    inferred_value 1024
+};
+
+cdl_option CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA {
+    inferred_value FLASH
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
+    inferred_value 64
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
+    inferred_value 256
+};
+
+cdl_option CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK {
+    inferred_value 0
+};
+
+cdl_option CYGBLD_ISO_STRTOK_R_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/bsdstring.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_DNS_HEADER {
+    inferred_value 1 <cyg/ns/dns/dns.h>
+};
+
+cdl_option CYGPKG_NS_DNS_BUILD {
+    inferred_value 0
+};
+
+
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/misc/redboot_RAM.ecm
@@ -0,0 +1,142 @@
+cdl_savefile_version 1;
+cdl_savefile_command cdl_savefile_version {};
+cdl_savefile_command cdl_savefile_command {};
+cdl_savefile_command cdl_configuration { description hardware template package };
+cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value };
+
+cdl_configuration eCos {
+    description "" ;
+    hardware    moab ;
+    template    redboot ;
+    package -hardware CYGPKG_HAL_POWERPC current ;
+    package -hardware CYGPKG_HAL_POWERPC_PPC40x current ;
+    package -hardware CYGPKG_HAL_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX current ;
+    package -hardware CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_PPC405 current ;
+    package -hardware CYGPKG_DEVS_ETH_PHY current ;
+    package -hardware CYGPKG_IO_PCI current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307 current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB current ;
+    package -template CYGPKG_HAL current ;
+    package -template CYGPKG_INFRA current ;
+    package -template CYGPKG_REDBOOT current ;
+    package -template CYGPKG_ISOINFRA current ;
+    package -template CYGPKG_LIBC_STRING current ;
+    package -template CYGPKG_NS_DNS current ;
+    package -template CYGPKG_CRC current ;
+    package CYGPKG_IO_ETH_DRIVERS current ;
+    package CYGPKG_IO_FLASH current ;
+    package CYGPKG_IO_WALLCLOCK current ;
+};
+
+cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS {
+    inferred_value 0
+};
+
+cdl_option CYGHWR_DEVS_ETH_PHY_DP83847 {
+    inferred_value 1
+};
+
+cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE {
+    user_value 4096
+};
+
+cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT {
+    user_value 0
+};
+
+cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_HAL_DCACHE_STARTUP_MODE {
+    inferred_value WRITETHRU
+};
+
+cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_POWERPC_RESET_USES_JUMP {
+    inferred_value 1
+};
+
+cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
+    inferred_value 0
+};
+
+cdl_component CYGBLD_BUILD_REDBOOT {
+    user_value 1
+};
+
+cdl_option CYGBLD_REDBOOT_MAX_MEM_SEGMENTS {
+    inferred_value 2
+};
+
+cdl_option CYGBLD_REDBOOT_MIN_IMAGE_SIZE {
+    user_value 0x00080000
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
+    inferred_value 2048
+};
+
+cdl_option CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA {
+    inferred_value EEPROM
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
+    inferred_value 64
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
+    inferred_value 256
+};
+
+cdl_option CYGBLD_ISO_STRTOK_R_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/bsdstring.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_DNS_HEADER {
+    inferred_value 1 <cyg/ns/dns/dns.h>
+};
+
+cdl_option CYGPKG_NS_DNS_BUILD {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_IO_FLASH_READ_INDIRECT {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_IO_FLASH_VERIFY_PROGRAM {
+    inferred_value 0
+};
+
+cdl_component CYGSEM_DEVS_FLASH_POWERPC_MOAB_MAIN {
+    user_value 1
+};
+
+
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/misc/redboot_ROM.ecm
@@ -0,0 +1,96 @@
+cdl_savefile_version 1;
+cdl_savefile_command cdl_savefile_version {};
+cdl_savefile_command cdl_savefile_command {};
+cdl_savefile_command cdl_configuration { description hardware template package };
+cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value };
+
+cdl_configuration eCos {
+    description "" ;
+    hardware    moab ;
+    template    redboot ;
+    package -hardware CYGPKG_HAL_POWERPC current ;
+    package -hardware CYGPKG_HAL_POWERPC_PPC40x current ;
+    package -hardware CYGPKG_HAL_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX current ;
+    package -template CYGPKG_HAL current ;
+    package -template CYGPKG_INFRA current ;
+    package -template CYGPKG_REDBOOT current ;
+    package -template CYGPKG_ISOINFRA current ;
+    package -template CYGPKG_LIBC_STRING current ;
+    package -template CYGPKG_NS_DNS current ;
+    package -template CYGPKG_CRC current ;
+};
+
+cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS {
+    inferred_value 0
+};
+
+cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE {
+    user_value 4096
+};
+
+cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT {
+    user_value 0
+};
+
+cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM {
+    inferred_value 0
+};
+
+cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_ROM_MONITOR {
+    inferred_value 1
+};
+
+cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
+    user_value 0
+};
+
+cdl_component CYG_HAL_STARTUP {
+    user_value ROM
+};
+
+cdl_option CYGHWR_HAL_POWERPC_CPU_SPEED {
+    user_value 250
+};
+
+cdl_component CYGBLD_BUILD_REDBOOT {
+    user_value 1
+};
+
+cdl_option CYGBLD_ISO_STRTOK_R_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/bsdstring.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_DNS_HEADER {
+    inferred_value 1 <cyg/ns/dns/dns.h>
+};
+
+cdl_option CYGPKG_NS_DNS_BUILD {
+    inferred_value 0
+};
+
+
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/misc/redboot_ROMRAM.ecm
@@ -0,0 +1,174 @@
+cdl_savefile_version 1;
+cdl_savefile_command cdl_savefile_version {};
+cdl_savefile_command cdl_savefile_command {};
+cdl_savefile_command cdl_configuration { description hardware template package };
+cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value };
+cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value };
+
+cdl_configuration eCos {
+    description "" ;
+    hardware    moab ;
+    template    redboot ;
+    package -hardware CYGPKG_HAL_POWERPC current ;
+    package -hardware CYGPKG_HAL_POWERPC_PPC40x current ;
+    package -hardware CYGPKG_HAL_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_FLASH_ATMEL_AT49XXXX current ;
+    package -hardware CYGPKG_DEVS_FLASH_TOSHIBA_TC58XXX current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_MOAB current ;
+    package -hardware CYGPKG_DEVS_ETH_POWERPC_PPC405 current ;
+    package -hardware CYGPKG_DEVS_ETH_PHY current ;
+    package -hardware CYGPKG_IO_PCI current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_DALLAS_DS1307 current ;
+    package -hardware CYGPKG_DEVICES_WALLCLOCK_POWERPC_MOAB current ;
+    package -template CYGPKG_HAL current ;
+    package -template CYGPKG_INFRA current ;
+    package -template CYGPKG_REDBOOT current ;
+    package -template CYGPKG_ISOINFRA current ;
+    package -template CYGPKG_LIBC_STRING current ;
+    package -template CYGPKG_NS_DNS current ;
+    package -template CYGPKG_CRC current ;
+    package CYGPKG_IO_ETH_DRIVERS current ;
+    package CYGPKG_IO_WALLCLOCK current ;
+    package CYGPKG_IO_FLASH current ;
+};
+
+cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS {
+    inferred_value 0
+};
+
+cdl_option CYGNUM_IO_ETH_DRIVERS_NUM_PKT {
+    user_value 32
+};
+
+cdl_option CYGSEM_IO_ETH_DRIVERS_WARN {
+    user_value 0
+};
+
+cdl_option CYGHWR_DEVS_ETH_PHY_DP83847 {
+    inferred_value 1
+};
+
+cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE {
+    user_value 4096
+};
+
+cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT {
+    user_value 0
+};
+
+cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_HAL_DCACHE_STARTUP_MODE {
+    inferred_value WRITETHRU
+};
+
+cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_ROM_MONITOR {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_HAL_POWERPC_RESET_USES_JUMP {
+    inferred_value 1
+};
+
+cdl_option CYGHWR_HAL_POWERPC_ENABLE_MMU {
+    inferred_value 0
+};
+
+cdl_component CYG_HAL_STARTUP {
+    user_value ROMRAM
+};
+
+cdl_component CYGBLD_BUILD_REDBOOT {
+    user_value 1
+};
+
+cdl_option CYGBLD_REDBOOT_MAX_MEM_SEGMENTS {
+    inferred_value 2
+};
+
+cdl_option CYGNUM_REDBOOT_NETWORKING_MAX_PKTBUF {
+    user_value 8
+};
+
+cdl_option CYGSEM_REDBOOT_PLF_STARTUP {
+    user_value 0
+};
+
+cdl_option CYGBLD_REDBOOT_MIN_IMAGE_SIZE {
+    user_value 0x00080000
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
+    inferred_value 2048
+};
+
+cdl_option CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA {
+    inferred_value EEPROM
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
+    inferred_value 64
+};
+
+cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
+    inferred_value 256
+};
+
+cdl_option CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK {
+    inferred_value 0
+};
+
+cdl_option CYGBLD_ISO_STRTOK_R_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/bsdstring.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER {
+    inferred_value 1 <cyg/libc/string/string.h>
+};
+
+cdl_option CYGBLD_ISO_DNS_HEADER {
+    inferred_value 1 <cyg/ns/dns/dns.h>
+};
+
+cdl_option CYGPKG_NS_DNS_BUILD {
+    inferred_value 0
+};
+
+cdl_option CYGSEM_IO_FLASH_READ_INDIRECT {
+    inferred_value 1
+};
+
+cdl_option CYGSEM_IO_FLASH_CHATTER {
+    user_value 0
+};
+
+cdl_option CYGSEM_IO_FLASH_VERIFY_PROGRAM {
+    inferred_value 0
+};
+
+cdl_component CYGSEM_DEVS_FLASH_POWERPC_MOAB_MAIN {
+    user_value 1
+};
+
+
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/Makefile
@@ -0,0 +1,27 @@
+#
+# Makefile for simple tests
+#
+
+CC = powerpc-eabi-gcc
+CFLAGS = -mcpu=405 -msoft-float -O2 -g
+LDFLAGS = -msoft-float -mcpu=405 -g -nostdlib -Wl,-static -Wl,-Map,$@.map
+
+TESTS = test_sdram_ocm.elf test_sdram_dram.elf test_flash.elf
+
+.S.o:
+	$(CC) $(CFLAGS) -c -o $@ $*.S
+
+all: ${TESTS}
+
+TEST_SDRAM_OBJS = start.o tty.o sdram_test.o
+test_sdram_ocm.elf: ${TEST_SDRAM_OBJS}
+	$(CC) $(LDFLAGS) -Tppc_ocm.ld -o $@ ${TEST_SDRAM_OBJS}
+test_sdram_dram.elf: ${TEST_SDRAM_OBJS}
+	$(CC) $(LDFLAGS) -Tppc_dram.ld -o $@ ${TEST_SDRAM_OBJS}
+
+TEST_FLASH_OBJS = start.o tty.o flash_test.o
+test_flash.elf: ${TEST_FLASH_OBJS}
+	$(CC) $(LDFLAGS) -Tppc_ocm.ld -o $@ ${TEST_FLASH_OBJS}
+
+clean:
+	rm -f *.o *~ ${TESTS} *.map *.elf
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/flash_test.c
@@ -0,0 +1,52 @@
+//
+// Simple (boot) FLASH test
+//
+//-----------------------------------------------------------------
+// Copyright (C) 2003, Gary Thomas <gary@mlbassoc.com>
+//-----------------------------------------------------------------
+
+#define BOOT_FLASH 0xFFF80000   // 512K
+#define SETUP1         0x5555
+#define SETUP2         0x2AAA
+#define SETUP_CODE1      0xAA
+#define SETUP_CODE2      0x55
+#define QUERY_START      0x90
+#define QUERY_END        0xF0
+#define MANUF_ID            0
+#define PART_ID             1
+
+static void
+hang(void)
+{
+    while (1) ;
+}
+
+void
+run_test(void)
+{
+    volatile unsigned char *flash = (volatile unsigned char *)BOOT_FLASH;
+    unsigned char info[2];
+
+    tty_puts("FLASH test started\n");
+
+    // Send "query" command sequence
+    flash[SETUP1] = SETUP_CODE1;
+    flash[SETUP2] = SETUP_CODE2;
+    flash[SETUP1] = QUERY_START;
+
+    // Fetch query information
+    info[0] = flash[MANUF_ID];
+    info[1] = flash[PART_ID];
+
+    // Send "query done" command sequence
+    flash[SETUP1] = SETUP_CODE1;
+    flash[SETUP2] = SETUP_CODE2;
+    flash[SETUP1] = QUERY_END;
+
+    tty_puts("FLASH query info = ");
+    tty_puthex(info[0]<<8 | info[1]);
+    tty_puts("\n");
+
+    // Done
+    tty_puts("Done\n");
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/ppc.inc
@@ -0,0 +1,50 @@
+//-----------------------------------------------------------------
+// Copyright (C) 2003, Gary Thomas <gary@mlbassoc.com>
+//-----------------------------------------------------------------
+
+#------------------------------------------------------------------------------
+# Easier to read names for the registers
+
+	.equ	r0, 0
+	.equ	r1, 1
+	.equ	r2, 2
+	.equ	r3, 3
+	.equ	r4, 4
+	.equ	r5, 5
+	.equ	r6, 6
+	.equ	r7, 7
+	.equ	r8, 8
+	.equ	r9, 9
+	.equ	r10, 10
+	.equ	r11, 11
+	.equ	r12, 12
+	.equ	r13, 13
+	.equ	r14, 14
+	.equ	r15, 15
+	.equ	r16, 16
+	.equ	r17, 17
+	.equ	r18, 18
+	.equ	r19, 19
+	.equ	r20, 20
+	.equ	r21, 21
+	.equ	r22, 22
+	.equ	r23, 23
+	.equ	r24, 24
+	.equ	r25, 25
+	.equ	r26, 26
+	.equ	r27, 27
+	.equ	r28, 28
+	.equ	r29, 29
+	.equ	r30, 30
+	.equ	r31, 31
+
+	.equ	sp, r1
+
+#------------------------------------------------------------------------------
+# Some useful coding macros
+
+	# Load immediate word, has to be done with 2 instructions
+	.macro	lwi	reg,val
+	lis	\reg,\val@H
+	ori	\reg,\reg,\val@L
+	.endm
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/ppc_dram.ld
@@ -0,0 +1,21 @@
+ENTRY(start)
+
+MEMORY
+{
+    ram : ORIGIN = 0x0, LENGTH = 0x1000
+}
+
+SECTIONS
+{
+    .text 0x00000000 : { _stext = .; *(.text*) *(.gnu.warning) *(.gnu.linkonce*) *(.init) } > ram _etext = .; PROVIDE (etext = .);
+    .fini ALIGN (0x4) : { . = .; *(.fini) } > ram
+    .rodata1 ALIGN (0x8) : { . = .; *(.rodata1*) } > ram
+    .rodata ALIGN (0x8) : { . = .; *(.rodata*) } > ram
+    .fixup ALIGN (0x4) : { __FIXUP_START__ = ABSOLUTE(.); *(.fixup) __FIXUP_END__ = ABSOLUTE(.);} > ram
+    .gcc_except_table ALIGN (0x1) : { __EXCEPT_START__ = ABSOLUTE(.); *(.gcc_except_table) __EXCEPT_END__ = ABSOLUTE(.);} > ram
+    .data ALIGN (0x8) : { __ram_data_start = ABSOLUTE(.); *(.data*) __GOT1_START__ = ABSOLUTE(.); *(.got1) __GOT1_END__ = ABSOLUTE(.); . = ALIGN(8); __CTOR_LIST__ = ABSOLUTE(.); KEEP(*(SORT(.ctors*))) __CTOR_END__ = ABSOLUTE(.); __DTOR_LIST__ = ABSOLUTE(.); KEEP(*(SORT(.dtors*))) __DTOR_END__ = ABSOLUTE(.); . = ALIGN(8); KEEP(*( SORT (.ecos.table.*))) ; . = ALIGN(4); *( .2ram.*) ; __GOT2_START__ = ABSOLUTE(.); *(.got2) __GOT2_END__ = ABSOLUTE(.); __GOT_START = ABSOLUTE(.); _GLOBAL_OFFSET_TABLE_ = ABSOLUTE(. + 32768); _SDA_BASE_ = ABSOLUTE(.); *(.got.plt) *(.got) __GOT_END__ = ABSOLUTE(.); *(.dynamic) *(.eh_frame) __SDATA_START__ = ABSOLUTE(.); *(.sdata) *(.sdata.*) __SDATA2_START__ = ABSOLUTE(.); *(.sdata2*) } > ram __rom_data_start = LOADADDR(.data); __ram_data_end = .; PROVIDE(__ram_data_end = .); _edata = .; PROVIDE (edata = .);
+    .sbss ALIGN (0x4) : { __sbss_start = ABSOLUTE (.); __SBSS_START__ = ABSOLUTE(.); *(.sbss.*) __SBSS_END__ = ABSOLUTE(.); __SBSSx_START__ = ABSOLUTE(.); *(.sbss*) __SBSSx_END__ = ABSOLUTE(.); *(.scommon*) __sbss_end = ABSOLUTE (.); } > ram
+    .bss ALIGN (0x10) : { __bss_start = ABSOLUTE (.); . = .; *(.dynbss*) *(.bss*) *(COMMON) __bss_end = ABSOLUTE (.); } > ram
+    __heap1 = ALIGN (0x8);
+    . = ALIGN(4); _end = .; PROVIDE (end = .);
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/ppc_ocm.ld
@@ -0,0 +1,21 @@
+ENTRY(start)
+
+MEMORY
+{
+    ram : ORIGIN = 0xD0000000, LENGTH = 0x1000
+}
+
+SECTIONS
+{
+    .text 0xD0000000 : { _stext = .; *(.text*) *(.gnu.warning) *(.gnu.linkonce*) *(.init) } > ram _etext = .; PROVIDE (etext = .);
+    .fini ALIGN (0x4) : { . = .; *(.fini) } > ram
+    .rodata1 ALIGN (0x8) : { . = .; *(.rodata1*) } > ram
+    .rodata ALIGN (0x8) : { . = .; *(.rodata*) } > ram
+    .fixup ALIGN (0x4) : { __FIXUP_START__ = ABSOLUTE(.); *(.fixup) __FIXUP_END__ = ABSOLUTE(.);} > ram
+    .gcc_except_table ALIGN (0x1) : { __EXCEPT_START__ = ABSOLUTE(.); *(.gcc_except_table) __EXCEPT_END__ = ABSOLUTE(.);} > ram
+    .data ALIGN (0x8) : { __ram_data_start = ABSOLUTE(.); *(.data*) __GOT1_START__ = ABSOLUTE(.); *(.got1) __GOT1_END__ = ABSOLUTE(.); . = ALIGN(8); __CTOR_LIST__ = ABSOLUTE(.); KEEP(*(SORT(.ctors*))) __CTOR_END__ = ABSOLUTE(.); __DTOR_LIST__ = ABSOLUTE(.); KEEP(*(SORT(.dtors*))) __DTOR_END__ = ABSOLUTE(.); . = ALIGN(8); KEEP(*( SORT (.ecos.table.*))) ; . = ALIGN(4); *( .2ram.*) ; __GOT2_START__ = ABSOLUTE(.); *(.got2) __GOT2_END__ = ABSOLUTE(.); __GOT_START = ABSOLUTE(.); _GLOBAL_OFFSET_TABLE_ = ABSOLUTE(. + 32768); _SDA_BASE_ = ABSOLUTE(.); *(.got.plt) *(.got) __GOT_END__ = ABSOLUTE(.); *(.dynamic) *(.eh_frame) __SDATA_START__ = ABSOLUTE(.); *(.sdata) *(.sdata.*) __SDATA2_START__ = ABSOLUTE(.); *(.sdata2*) } > ram __rom_data_start = LOADADDR(.data); __ram_data_end = .; PROVIDE(__ram_data_end = .); _edata = .; PROVIDE (edata = .);
+    .sbss ALIGN (0x4) : { __sbss_start = ABSOLUTE (.); __SBSS_START__ = ABSOLUTE(.); *(.sbss.*) __SBSS_END__ = ABSOLUTE(.); __SBSSx_START__ = ABSOLUTE(.); *(.sbss*) __SBSSx_END__ = ABSOLUTE(.); *(.scommon*) __sbss_end = ABSOLUTE (.); } > ram
+    .bss ALIGN (0x10) : { __bss_start = ABSOLUTE (.); . = .; *(.dynbss*) *(.bss*) *(COMMON) __bss_end = ABSOLUTE (.); } > ram
+    __heap1 = ALIGN (0x8);
+    . = ALIGN(4); _end = .; PROVIDE (end = .);
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/sdram_test.c
@@ -0,0 +1,501 @@
+//
+// Simple SDRAM test
+//
+//-----------------------------------------------------------------
+// Copyright (C) 2003, Gary Thomas <gary@mlbassoc.com>
+//-----------------------------------------------------------------
+
+#define DRAM_START      0x00010000
+#define DRAM_END        0x00700000
+
+#define MAX_ERRS        16
+#define SPIN_TIME       0x800
+
+//#define DO_SPIN
+#define TEST_LONGS
+#define TEST_SHORTS
+#define TEST_BYTES
+#define TEST_REFRESH
+#define TEST_PARALLEL
+//#define TEST_RANDOM
+
+typedef unsigned long munge_fun(unsigned long);
+
+void
+spin(void)
+{
+#ifdef DO_SPIN
+    static char spin_chars[] = "|/-\\|-";
+    static int tick = 0;
+    static int times = 0;
+
+    if (++times == SPIN_TIME) {
+        tty_putc(spin_chars[tick++]);
+        tty_putc(0x08);
+        if (tick >= sizeof(spin_chars)) {
+            tick = 0;
+        }
+        times = 0;
+    }
+#endif
+}
+
+unsigned long
+nop(unsigned long val)
+{
+    spin();
+    return val;
+}
+
+unsigned long
+toggle(unsigned long val)
+{
+    spin();
+    return ~val;
+}
+
+unsigned long
+inc_addr(unsigned long val)
+{
+    spin();
+    return val + sizeof(unsigned long);
+}
+
+void
+idle(void)
+{
+    int i;
+    for (i = 0;  i < 1000000;  i++) ;
+}
+
+#ifdef TEST_LONGS
+void
+test_longs(char *title, unsigned long _orig_pat, 
+           unsigned long *start_addr, unsigned long *end_addr,
+           munge_fun *fun, int _delay, int loops)
+{
+    unsigned long *p;
+    unsigned long val, pat;
+    int errs, idle, delay;
+
+    tty_puts(title);
+#ifdef DO_SPIN
+    tty_puts("\n");
+#endif
+
+    // Fill SDRAM with various patterns
+    p = start_addr;
+    pat = _orig_pat;
+    while (p != end_addr) {
+        *p++ = pat;
+        pat = (*fun)(pat);
+    }
+
+    while (loops-- > 0) {
+        tty_puts("<");
+        delay = _delay;
+        while (delay-- > 0) {
+            idle = 0xF000000;
+            while (--idle > 0) ;
+        }
+        tty_puts(">");
+
+        // Test SDRAM
+        p = start_addr;
+        pat = _orig_pat;
+        errs = 0;
+        while (p != end_addr) {
+            if ((val = *p++) != pat) {
+                if (++errs < MAX_ERRS) {
+                    tty_puts("\nFailed at ");
+                    tty_puthex(p-1);
+                    tty_puts(", read: ");
+                    tty_puthex(val);
+                    tty_puts(", expected: ");
+                    tty_puthex(pat);
+                }
+            }
+            pat = (*fun)(pat);
+        }
+
+        tty_puts(" - done");
+        if (errs) {
+            tty_puts(" with ");
+            tty_puthex(errs);
+            tty_puts(" errors");
+        }
+        tty_puts("\n");
+    }
+}
+#endif
+
+#ifdef TEST_SHORTS
+void
+test_shorts(char *title, unsigned short _orig_pat, 
+            unsigned short *start_addr, unsigned short *end_addr,
+            munge_fun *fun, int _delay, int loops)
+{
+    unsigned short *p;
+    unsigned short val, pat;
+    int errs, idle, delay;
+
+    tty_puts(title);
+#ifdef DO_SPIN
+    tty_puts("\n");
+#endif
+
+    // Fill SDRAM with various patterns
+    p = start_addr;
+    pat = _orig_pat;
+    while (p != end_addr) {
+        *p++ = pat;
+        pat = (*fun)(pat);
+    }
+
+    while (loops-- > 0) {
+        tty_puts("<");
+        delay = _delay;
+        while (delay-- > 0) {
+            idle = 0xF000000;
+            while (--idle > 0) ;
+        }
+        tty_puts(">");
+
+        // Test SDRAM
+        p = start_addr;
+        pat = _orig_pat;
+        errs = 0;
+        while (p != end_addr) {
+            if ((val = *p++) != pat) {
+                if (++errs < MAX_ERRS) {
+                    tty_puts("\nFailed at ");
+                    tty_puthex(p-1);
+                    tty_puts(", read: ");
+                    tty_puthex(val);
+                    tty_puts(", expected: ");
+                    tty_puthex(pat);
+                }
+            }
+            pat = (*fun)(pat);
+        }
+
+        tty_puts(" - done");
+        if (errs) {
+            tty_puts(" with ");
+            tty_puthex(errs);
+            tty_puts(" errors");
+        }
+        tty_puts("\n");
+    }
+}
+#endif
+
+#ifdef TEST_BYTES
+void
+test_bytes(char *title, unsigned char _orig_pat, 
+           unsigned char *start_addr, unsigned char *end_addr,
+           munge_fun *fun, int _delay, int loops)
+{
+    unsigned char *p;
+    unsigned char val, pat;
+    int errs, idle, delay;
+
+    tty_puts(title);
+#ifdef DO_SPIN
+    tty_puts("\n");
+#endif
+
+    // Fill SDRAM with various patterns
+    p = start_addr;
+    pat = _orig_pat;
+    while (p != end_addr) {
+        *p++ = pat;
+        pat = (*fun)(pat);
+    }
+
+    while (loops-- > 0) {
+        tty_puts("<");
+        delay = _delay;
+        while (delay-- > 0) {
+            idle = 0xF000000;
+            while (--idle > 0) ;
+        }
+        tty_puts(">");
+
+        // Test SDRAM
+        p = start_addr;
+        pat = _orig_pat;
+        errs = 0;
+        while (p != end_addr) {
+            if ((val = *p++) != pat) {
+                if (++errs < MAX_ERRS) {
+                    tty_puts("\nFailed at ");
+                    tty_puthex(p-1);
+                    tty_puts(", read: ");
+                    tty_puthex(val);
+                    tty_puts(", expected: ");
+                    tty_puthex(pat);
+                }
+            }
+            pat = (*fun)(pat);
+        }
+
+        tty_puts(" - done");
+        if (errs) {
+            tty_puts(" with ");
+            tty_puthex(errs);
+            tty_puts(" errors");
+        }
+        tty_puts("\n");
+    }
+}
+#endif
+
+#ifdef TEST_PARALLEL
+void
+parallel_longs(unsigned long _orig_pat, 
+               unsigned long *start_buf1, 
+               unsigned long *start_buf2,
+               unsigned long *end_addr,
+               munge_fun *fun)
+{
+    unsigned long *p1, *p2;
+    unsigned long pat, v1, v2;
+    int errs, loops;
+
+    tty_puts("Parallel buffers\n");
+    // Fill buffers
+    p1 = start_buf1;
+    p2 = start_buf2;
+    pat = _orig_pat;
+    while (p2 != end_addr) {
+        *p1++ = pat;
+        *p2++ = ~pat;
+        pat = (*fun)(pat);
+    }
+
+    for (loops = 0;  loops < 4;  loops++) {
+        // Compare buffers
+        p1 = start_buf1;
+        p2 = start_buf2;
+        pat = _orig_pat;
+        errs = 0;
+        while (p2 != end_addr) {
+            if (((v1 = *p1) != pat) ||
+                ((v2 = *p2) != ~pat)) {
+                if (++errs < MAX_ERRS) {
+                    tty_puts("\nFailed at ");
+                    tty_puthex(p1);
+                    tty_puts(", v1: ");
+                    tty_puthex(v1);
+                    tty_puts(", v2: ");
+                    tty_puthex(v2);
+                }
+            }
+            p1++;  p2++;
+            pat = (*fun)(pat);
+        }
+        p1 = start_buf1;
+        p2 = start_buf2;
+        pat = _orig_pat;
+        errs = 0;
+        while (p2 != end_addr) {
+            if (((v1 = *p1) != pat) ||
+                ((v2 = *p1) != pat)) {
+                if (++errs < MAX_ERRS) {
+                    tty_puts("\nFailed at ");
+                    tty_puthex(p1);
+                    tty_puts(", v1: ");
+                    tty_puthex(v1);
+                    tty_puts(", v2: ");
+                    tty_puthex(v2);
+                }
+            }
+            p1++;  p2++;
+            pat = (*fun)(pat);
+        }
+        tty_puts(" - done");
+        if (errs) {
+            tty_puts(" with ");
+            tty_puthex(errs);
+            tty_puts(" errors");
+        }
+        tty_puts("\n");
+    }
+}
+#endif
+
+#ifdef TEST_RANDOM
+// Not really random, but noisy
+
+unsigned long pseudo_random_data[] = {
+#if 0
+    0x38810008, 0x80690000, 0x8129001C, 0x7D2903A6,
+    0x4E800421, 0x2C030000, 0x4082FFE4, 0x80010024,
+    0x83E1001C, 0x7C0803A6, 0x38210020, 0x4E800020,
+    0x9421FFD0, 0x7C0802A6, 0x3D200000, 0x93C10028,
+    0x90010034, 0x3BC948F0, 0x801E0430, 0x9361001C,
+    0x2C000000, 0x93A10024, 0x93E1002C, 0x93210014,
+    0x93410018, 0x93810020, 0x3BA00000, 0x3B600000,
+    0x3BE00000, 0x40820318, 0x3B410008, 0x3F800000,
+    0x7FD9F378, 0x813C48F0, 0x7F44D378, 0x80690000,
+    0x8129001C, 0x7D2903A6, 0x4E800421, 0x2C030000,
+    0x418202C8, 0x89610008, 0x3BFF0001, 0x5560063E,
+    0x2C000002, 0x4182023C, 0x41810258, 0x2C000001,
+    0x41820224, 0x2C1D0000, 0x4182FFBC, 0x3FC00000,
+    0x813E48F0, 0x3C800000, 0x80690000, 0x8129001C,
+    0x38844CF8, 0x7D2903A6, 0x4E800421, 0x2C030000,
+    0x3BFE48F0, 0x3860FFFD, 0x40820030, 0x80010034 
+#else
+    /* 0x0010B000: */0x41810008, 0x540B063E, 0x5560063E, 0x7C030000,
+    /* 0x0010B010: */0x7C601850, 0x4C820020, 0x419E0008, 0x4200FFAC,
+    /* 0x0010B020: */0x38600000, 0x4E800020, 0x9421FFE0, 0x7C0802A6, 
+    /* 0x0010B030: */0x3D200000, 0x93C10018, 0x90010024, 0x3BC93200, 
+    /* 0x0010B040: */0x801E0034, 0x93810010, 0x93A10014, 0x93E1001C, 
+    /* 0x0010B050: */0x7C7D1B78, 0x7C0903A6, 0x3860FFFF, 0x7C9F2378,
+    /* 0x0010B060: */0x4E800421, 0x2C1D0002, 0x7C7C1B78, 0x41820060, 
+    /* 0x0010B070: */0x3C60FFF9, 0x3863FBFC, 0x4BFFEEA9, 0x3D200000,
+    /* 0x0010B080: */0x80093880, 0x3C60FFF9, 0x2C000000, 0x3863FC1C,
+    /* 0x0010B090: */0x7F84E378, 0x40820030, 0x3C60FFF9, 0x3863FC20,
+    /* 0x0010B0A0: */0x4BFFEE81, 0x80010024, 0x83810010, 0x83A10014, 
+    /* 0x0010B0B0: */0x83C10018, 0x83E1001C, 0x7C0803A6, 0x38210020, 
+    /* 0x0010B0C0: */0x4E800020, 0x4BFFEE5D, 0x4BFFFFDC, 0x807F0004, 
+    /* 0x0010B0D0: */0x3C80FFF9, 0x3884FC24, 0x38A00003, 0x48001C09, 
+    /* 0x0010B0E0: */0x2C030000, 0x4082001C, 0x3D200000, 0x90693880, 
+    /* 0x0010B0F0: */0x38000001, 0x3D200000, 0x9009389C, 0x4BFFFFA8, 
+    /* 0x0010B100: */0x807F0004, 0x38810008, 0x38A00000, 0x38C00000,
+    /* 0x0010B110: */0x48001625, 0x2C030000, 0x41820050, 0x80010008, 
+    /* 0x0010B120: */0x2C000000, 0x40820034, 0x801E0034, 0x38600000, 
+    /* 0x0010B130: */0x7C0903A6, 0x4E800421, 0x83DE0030, 0x80610008, 
+    /* 0x0010B140: */0x7FC903A6, 0x4E800421, 0x80010008, 0x7C00E000,
+    /* 0x0010B150: */0x4082FFA0, 0x4BFFFF50, 0x3C60FFF9, 0x809F0004,
+    /* 0x0010B160: */0x3863FC28, 0x4BFFFF60, 0x3C60FFF9, 0x809F0004,
+    /* 0x0010B170: */0x3863FC4C, 0x4BFFFF50, 0x9421FFE8, 0x7C0802A6,
+    /* 0x0010B180: */0x3D200000, 0x93C10010, 0x9001001C, 0x3BC93200,
+    /* 0x0010B190: */0x3D200000, 0x80093880, 0x93E10014, 0x2C000000,
+    /* 0x0010B1A0: */0x7C7F1B78, 0x93A1000C, 0x3860FFFF, 0x4182004C,
+    /* 0x0010B1B0: */0x813E0014, 0x7FE4FB78, 0x2C090000, 0x41820030,
+    /* 0x0010B1C0: */0x80690000, 0x8129000C, 0x7D2903A6, 0x4E800421,
+    /* 0x0010B1D0: */0x8001001C, 0x83A1000C, 0x83C10010, 0x83E10014,
+    /* 0x0010B1E0: */0x7C0803A6, 0x38210018, 0x4E800020, 0x813E0018,
+    /* 0x0010B1F0: */0x7FE4FB78, 0x4BFFFFCC, 0x801E0034, 0x7C0903A6 
+
+#endif
+};
+
+void
+random_longs(unsigned long *start, unsigned long end)
+{
+    unsigned long *dp, *random, *random_end;
+    unsigned long v1, v2;
+    int errs, tries, total;
+
+    random_end = (unsigned long *)((unsigned long)pseudo_random_data + sizeof(pseudo_random_data));
+
+    dp = start;  random = pseudo_random_data;
+    tty_putc('\r');
+    tries = 0;
+    while (dp != end) {
+        *dp++ = *random++;
+        if (random == random_end) {
+            random = pseudo_random_data;
+            if (++tries == 0x100) {
+                tty_putc('.');            
+                tries = 0;
+                idle();
+            }
+        }
+    }
+    tty_putc('\r');
+
+    dp = start;  random = pseudo_random_data;
+    errs = 0;
+    while (dp != end) {
+        if ((v1 = *dp++) != (v2 = *random++)) {
+            if (++errs < MAX_ERRS) {
+                tty_puts("\nFailed at ");
+                tty_puthex(dp-1);
+                tty_puts(", v1: ");
+                tty_puthex(v1);
+                tty_puts(", v2: ");
+                tty_puthex(v2);
+                total = 0;
+                for (tries = 0;  tries < 1024;  tries++) {
+                    dp -= 2;  random -= 2;
+                    if ((v1 = *dp++) != (v2 = *random++)) total++;
+                    if ((v1 = *dp++) != (v2 = *random++)) total++;
+                }
+                tty_puts(", times: ");
+                tty_puthex(total);
+            }
+        }
+        if (random == random_end) {
+            random = pseudo_random_data;
+        }
+    }
+    if (errs) {
+        tty_puts("\nTotal errors: ");
+        tty_puthex(errs);
+        tty_puts("\n");
+    }
+}
+#endif
+
+void
+run_test(void)
+{
+    tty_puts("\nSDRAM test started\n");
+
+#ifdef TEST_RANDOM
+    tty_puts("Random data\n");
+    while(1) 
+    random_longs(DRAM_START, DRAM_END);
+#endif
+
+#ifdef TEST_PARALLEL
+    parallel_longs(DRAM_START, 
+                   (unsigned long *)DRAM_START, 
+                   (unsigned long *)(DRAM_START+((DRAM_END-DRAM_START)/2)), 
+                   (unsigned long *)DRAM_END, 
+                   inc_addr);
+    parallel_longs(0x00000000, 
+                   (unsigned long *)DRAM_START, 
+                   (unsigned long *)(DRAM_START+((DRAM_END-DRAM_START)/2)), 
+                   (unsigned long *)DRAM_END, 
+                   nop);
+#endif
+
+#ifdef TEST_LONG
+    tty_puts("*** Testing LONG\n");
+    test_longs("ZERO: ", 0x00000000, (unsigned long *)DRAM_START, (unsigned long *)DRAM_END, nop, 1, 1);
+    test_longs("ONES: ", 0xFFFFFFFF, (unsigned long *)DRAM_START, (unsigned long *)DRAM_END, nop, 1, 1);
+    test_longs("ALTS: ", 0x55AA55AA, (unsigned long *)DRAM_START, (unsigned long *)DRAM_END, toggle, 1, 1);
+    test_longs("ADDR: ", DRAM_START, (unsigned long *)DRAM_START, (unsigned long *)DRAM_END, inc_addr, 1, 1);
+#endif
+
+#ifdef TEST_SHORTS
+    tty_puts("*** Testing SHORT\n");
+    test_shorts("ZERO: ", 0x0000, (unsigned short *)DRAM_START, (unsigned short *)DRAM_END, nop, 1, 1);
+    test_shorts("ONES: ", 0xFFFF, (unsigned short *)DRAM_START, (unsigned short *)DRAM_END, nop, 1, 1);
+    test_shorts("ALTS: ", 0x55AA, (unsigned short *)DRAM_START, (unsigned short *)DRAM_END, toggle, 1, 1);
+    test_shorts("ADDR: ", 0, (unsigned short *)DRAM_START, (unsigned short *)DRAM_END, inc_addr, 1, 1);
+#endif
+
+#ifdef TEST_BYTES
+    tty_puts("*** Testing BYTE\n");
+    test_bytes("ZERO: ", 0x00, (unsigned char *)DRAM_START, (unsigned char *)DRAM_END, nop, 1, 1);
+    test_bytes("ONES: ", 0xFF, (unsigned char *)DRAM_START, (unsigned char *)DRAM_END, nop, 1, 1);
+    test_bytes("ALTS: ", 0xAA, (unsigned char *)DRAM_START, (unsigned char *)DRAM_END, toggle, 1, 1);
+    test_bytes("ADDR: ", 0, (unsigned char *)DRAM_START, (unsigned char *)DRAM_END, inc_addr, 1, 1);
+#endif
+
+#ifdef TEST_REFRESH
+    tty_puts("*** Testing REFRESH\n");
+    test_longs("LONG: ", DRAM_START, (unsigned long *)DRAM_START, (unsigned long *)DRAM_END, inc_addr, 32, 32);
+    test_shorts("SHORT: ", 0, (unsigned short *)DRAM_START, (unsigned short *)DRAM_END, inc_addr, 32, 32);
+    test_bytes("BYTE: ", 0, (unsigned char *)DRAM_START, (unsigned char *)DRAM_END, inc_addr, 32, 32);
+#endif
+
+    // Done
+    tty_puts("Done\n");
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/start.S
@@ -0,0 +1,59 @@
+//
+// Simple test code framework
+//
+//-----------------------------------------------------------------
+// Copyright (C) 2003, Gary Thomas <gary@mlbassoc.com>
+//-----------------------------------------------------------------
+
+#include "ppc.inc"        
+        
+#define GPIO0           0xEF600700        
+#define GPIO0_OR        GPIO0+0x000
+#define GPIO0_TCR       GPIO0+0x004
+
+        .text
+        .globl  start
+start:
+        mfdcr   r3,1018
+        mfdcr   r4,1019
+        
+        // Force caches to be totally clean
+        iccci   0,r3
+
+        lwi     r3,0
+        lwi     r4,0x8000
+10:     dccci   0,r3
+        addi    r3,r3,16
+        cmpw    r3,r4
+        bne     10b        
+
+//
+// Setup GPIO to drive LEDs
+//
+        lwi     r11,GPIO0_OR
+        li      r4,0x80
+        stw     r4,GPIO0_TCR-GPIO0(r11)
+        stw     r4,GPIO0_OR-GPIO0(r11)
+
+        // Setup and clear a stack used by the C code
+        lwi     sp,stack_base-4
+        li      r3,(stack-stack_base)/4
+        mtctr   r3
+        li      r0,0
+10:     stwu    r0,4(sp)
+        bdnz    10b
+
+        // Initialize the terminal environment
+        bl      tty_init
+
+        // Run the test code - it should never return                
+        bl      run_test
+
+        .section ".bss"
+stack_base:             
+        .rept   256
+        .byte   0
+        .endr        
+stack:  
+
+        .end
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/sa_tests/tty.c
@@ -0,0 +1,144 @@
+//
+// TTY support code
+//
+//-----------------------------------------------------------------
+// Copyright (C) 2003, Gary Thomas <gary@mlbassoc.com>
+//-----------------------------------------------------------------
+
+struct uart {
+    unsigned char rbr;
+#define thr rbr
+#define dll rbr
+    unsigned char dlm;
+#define ier dlm
+    unsigned char iir;
+#define fcr iir
+    unsigned char lcr;
+    unsigned char mcr;
+    unsigned char lsr;
+    unsigned char msr;
+    unsigned char scr;
+};
+
+// Control register defines
+// The interrupt enable register bits.
+#define SIO_IER_ERDAI   0x01            // enable received data available irq
+#define SIO_IER_ETHREI  0x02            // enable THR empty interrupt
+#define SIO_IER_ELSI    0x04            // enable receiver line status irq
+#define SIO_IER_EMSI    0x08            // enable modem status interrupt
+
+// The interrupt identification register bits.
+#define SIO_IIR_IP      0x01            // 0 if interrupt pending
+#define SIO_IIR_ID_MASK 0x0e            // mask for interrupt ID bits
+#define ISR_Tx  0x02
+#define ISR_Rx  0x04
+
+// The line status register bits.
+#define SIO_LSR_DR      0x01            // data ready
+#define SIO_LSR_OE      0x02            // overrun error
+#define SIO_LSR_PE      0x04            // parity error
+#define SIO_LSR_FE      0x08            // framing error
+#define SIO_LSR_BI      0x10            // break interrupt
+#define SIO_LSR_THRE    0x20            // transmitter holding register empty
+#define SIO_LSR_TEMT    0x40            // transmitter register empty
+#define SIO_LSR_ERR     0x80            // any error condition
+
+// The modem status register bits.
+#define SIO_MSR_DCTS  0x01              // delta clear to send
+#define SIO_MSR_DDSR  0x02              // delta data set ready
+#define SIO_MSR_TERI  0x04              // trailing edge ring indicator
+#define SIO_MSR_DDCD  0x08              // delta data carrier detect
+#define SIO_MSR_CTS   0x10              // clear to send
+#define SIO_MSR_DSR   0x20              // data set ready
+#define SIO_MSR_RI    0x40              // ring indicator
+#define SIO_MSR_DCD   0x80              // data carrier detect
+
+// The line control register bits.
+#define SIO_LCR_WLS0   0x01             // word length select bit 0
+#define SIO_LCR_WLS1   0x02             // word length select bit 1
+#define SIO_LCR_STB    0x04             // number of stop bits
+#define SIO_LCR_PEN    0x08             // parity enable
+#define SIO_LCR_EPS    0x10             // even parity select
+#define SIO_LCR_SP     0x20             // stick parity
+#define SIO_LCR_SB     0x40             // set break
+#define SIO_LCR_DLAB   0x80             // divisor latch access bit
+
+// The FIFO control register
+#define SIO_FCR_FCR0   0x01             // enable xmit and rcvr fifos
+#define SIO_FCR_FCR1   0x02             // clear RCVR FIFO
+#define SIO_FCR_FCR2   0x04             // clear XMIT FIFO
+
+void
+tty_init(void)
+{
+    volatile struct uart *uart = (volatile struct uart *)0xEF600300;
+    unsigned char lcr;
+
+    // Reset/clear interrupts
+    uart->ier = 0;
+
+    // Disable and clear FIFOs (need to enable to clear).
+    uart->fcr = (SIO_FCR_FCR0 | SIO_FCR_FCR1 | SIO_FCR_FCR2);
+    uart->fcr = 0;
+
+    // Set speed to 38400.
+    uart->lcr = SIO_LCR_WLS0 | SIO_LCR_WLS1 | SIO_LCR_DLAB;
+    uart->dll = 0x12;
+    uart->dlm = 0;
+
+    // 8-1-no parity.
+    uart->lcr = SIO_LCR_WLS0 | SIO_LCR_WLS1;
+
+    // Enable FIFOs (and clear them).
+    uart->fcr = (SIO_FCR_FCR0 | SIO_FCR_FCR1 | SIO_FCR_FCR2);
+}
+
+void
+tty_putc(char c)
+{
+    volatile struct uart *uart = (volatile struct uart *)0xEF600300;
+
+    do {
+    } while ((uart->lsr & SIO_LSR_TEMT) == 0);
+    uart->thr = c;
+}
+
+void
+tty_puts(char *s)
+{
+    char c;
+
+    while ((c = *s++) != '\0') {
+        tty_putc(c);
+        if (c == '\n') {
+            tty_putc('\r');
+        }
+    }
+}
+
+char
+tty_getc(void)
+{
+    volatile struct uart *uart = (volatile struct uart *)0xEF600300;
+
+    while ((uart->lsr & SIO_LSR_DR) == 0) ;
+    return uart->rbr;
+}
+
+void
+tty_puthex(unsigned long val)
+{
+    char hex[] = "0123456789ABCDEF";
+    char str[11];
+    char *s = &str[10];
+    int i;
+
+    *--s = '\0';
+    for (i = 0;  i < 8;  i++) {
+        *--s = hex[(val & 0x0F)];
+        val >>= 4;
+    }
+    *--s = 'x';
+    *--s = '0';
+    tty_puts(s);
+}
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/src/hal_aux.c
@@ -0,0 +1,262 @@
+//=============================================================================
+//
+//      hal_aux.c
+//
+//      HAL auxiliary objects and code; per platform
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   hmt
+// Contributors:hmt, gthomas
+// Date:        1999-06-08
+// Purpose:     HAL aux objects: startup tables.
+// Description: Tables for per-platform initialization
+//
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+#include <pkgconf/hal.h>
+
+#include <cyg/infra/cyg_type.h>
+#include <cyg/hal/hal_mem.h>            // HAL memory definitions
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
+#include <cyg/hal/ppc_regs.h>           // Platform registers
+#include <cyg/hal/hal_if.h>             // hal_if_init
+#include <cyg/hal/hal_intr.h>           // interrupt definitions
+#include <cyg/infra/cyg_ass.h>          // assertion macros
+#include <cyg/hal/hal_io.h>             // I/O macros
+#include <cyg/infra/diag.h>
+#include CYGHWR_MEMORY_LAYOUT_H
+
+#ifdef CYGPKG_REDBOOT
+#include <redboot.h>
+#endif
+
+// The memory map is weakly defined, allowing the application to redefine
+// it if necessary. The regions defined below are the minimum requirements.
+CYGARC_MEMDESC_TABLE CYGBLD_ATTRIB_WEAK = {
+    // Mapping for the TAMS MOAB development boards
+    CYGARC_MEMDESC_NOCACHE( 0xFFE00000, 0x00200000 ), // Boot ROM
+    CYGARC_MEMDESC_NOCACHE( 0xEF000000, 0x01000000 ), // CPU registers
+    CYGARC_MEMDESC_NOCACHE( 0xEE000000, 0x01000000 ), // PCI CFG 
+    CYGARC_MEMDESC_NOCACHE( 0xE8000000, 0x01000000 ), // PCI I/O
+    CYGARC_MEMDESC_NOCACHE( 0xA0000000, 0x10000000 ), // PCI Memory
+    CYGARC_MEMDESC_NOCACHE( _MOAB_NAND, 0x00100000 ), // Main [NAND] FLASH
+    CYGARC_MEMDESC_NOCACHE( _MOAB_OCM,  0x01000000 ), // OCM
+    CYGARC_MEMDESC_NOCACHE_PA( 0x80000000, 0x00000000, CYGMEM_REGION_ram_SIZE ), // Uncached version of RAM
+    CYGARC_MEMDESC_CACHE(   CYGMEM_REGION_ram, CYGMEM_REGION_ram_SIZE ), // Main memory
+    CYGARC_MEMDESC_TABLE_END
+};
+
+//--------------------------------------------------------------------------
+// Platform init code.
+void
+hal_platform_init(void)
+{
+}
+
+#ifdef CYGSEM_REDBOOT_PLF_STARTUP
+void
+cyg_plf_redboot_startup(void)
+{
+    cyg_uint32 gpio_ir;
+
+    HAL_READ_UINT32(GPIO_IR, gpio_ir);
+    if ((gpio_ir & 0x00080000) != 0) {
+        // Load RedBoot from NAND FLASH and execute it
+        script = "fi lo RedBoot;go\n";
+        script_timeout = 1;
+    }
+}
+#endif
+//
+// Initialize serial ports - called during hal_if_init()
+// Note: actual serial port support code is supported by the PPC405 variant layer
+//       Having this call here allows for additional platform specific additions
+//
+void
+cyg_hal_plf_comms_init(void)
+{
+    static int initialized = 0;
+
+    if (initialized)
+        return;
+    initialized = 1;
+
+    cyg_hal_var_serial_init();
+}
+
+//----------------------------------------------------------------------------
+// Reset.
+void
+_moab_reset(void)
+{
+    CYGARC_MTSPR(SPR_DBCR0, 0x30000000);  // Asserts system reset
+    while (1) ;
+}
+
+#ifdef CYGPKG_REDBOOT
+//----------------------------------------------------------------------------
+// Memory map [segment] support for RedBoot
+void 
+cyg_plf_memory_segment(int seg, unsigned char **start, unsigned char **end)
+{
+    if (seg == 1) {
+        *start = _MOAB_OCM;
+        *end = _MOAB_OCM + 0x1000;
+    } else {
+        diag_printf("** Invalid memory segment #%d - ignored\n", seg);
+        *start = NO_MEMORY;
+        *end = NO_MEMORY;
+    }
+}
+#endif
+
+//--------------------------------------------------------------------------
+// EEPROM support - 1024 bytes, treated as a single read/write block
+void
+read_eeprom(unsigned char *buf, int len)
+{
+    int i, page, page_addr, size;
+    cyg_uint8 addr[2];
+
+    if (len > CYGNUM_HAL_EEPROM_SIZE) {
+        diag_printf("%s - Illegal length: %d\n", __FUNCTION__, len);
+        return;
+    }
+#if CYGNUM_HAL_EEPROM_SIZE == 1024
+    // Read from start of EEPROM
+    for (i = 0;  i < len;  i += 4) {
+        page = 0xA9 + ((i >> 8) << 1);
+        if ((i % 256) == 0) {
+            addr[0] = 0x00;
+            if (!hal_ppc405_i2c_put_bytes(page, addr, 1)) {
+                diag_printf("%s - Can't select page %x\n", __FUNCTION__, page);
+                return;
+            }
+        }
+        if (!hal_ppc405_i2c_get_bytes(page, &buf[i], 4)) {
+            diag_printf("%s - Can't read byte %d\n", __FUNCTION__, i);
+            return;
+        }
+    }
+#else
+    // Read from start of EEPROM
+    page = 0xAF;  page_addr = 0;
+    for (i = 0;  i < len;  i += size) {
+        addr[0] = page_addr >> 8;  addr[1] = (page_addr & 0xFF);
+        size = (len - i);
+        if (size > 32) size = 32;
+        if (!hal_ppc405_i2c_put_bytes(page, &addr, 2)) {
+            diag_printf("%s - Can't select address %x\n", __FUNCTION__, page);
+            return;
+        }
+        if (!hal_ppc405_i2c_get_bytes(page, &buf[i], size)) {
+            diag_printf("%s - Can't read bytes\n", __FUNCTION__);
+            return;
+        }
+        page_addr += size;
+    }
+#endif
+#if 0
+    diag_printf("EEPROM data - read\n");
+    diag_dump_buf(buf, len);
+#endif
+}
+
+void
+write_eeprom(unsigned char *buf, int len)
+{
+    int i, j, page, page_addr, size, left;
+    cyg_uint8 addr[32+2];
+
+#if 0
+    diag_printf("EEPROM data - write\n");
+    diag_dump_buf(buf, len < 256 ? len : 256);
+#endif
+    if (len > CYGNUM_HAL_EEPROM_SIZE) {
+        diag_printf("%s - Illegal length: %d\n", __FUNCTION__, len);
+        return;
+    }
+#if CYGNUM_HAL_EEPROM_SIZE == 1024
+    // Write from start of EEPROM
+    for (left = len, i = 0;  i < len;  i += size, left -= size) {
+        addr[0] = i;
+        size = sizeof(addr)-1;
+        if (size > left) size = left;
+        for (j = 0;  j < size;  j++) {
+            addr[j+1] = buf[i+j];
+        }
+        page = 0xA8 + ((i >> 8) << 1);
+        if (!hal_ppc405_i2c_put_bytes(page, addr, size+1)) {
+            diag_printf("%s - Can't write byte - page: %x, addr: %d\n", __FUNCTION__, page, i);
+            return;
+        }
+        // Give device time to recover
+        CYGACC_CALL_IF_DELAY_US(10000);   // 10ms
+    }
+#else
+    // Write from start of EEPROM
+    page_addr = 0;  page = 0xAE;
+    for (i = 0;  i < len;  i += size) {
+        addr[0] = page_addr >> 8;  addr[1] = page_addr & 0xFF;
+        size = (len - i);
+        if (size > 32) size = 32;
+        for (j = 0;  j < size;  j++) {
+            addr[j+2] = buf[i+j];
+        }
+        if (!hal_ppc405_i2c_put_bytes(page, addr, size+2)) {
+            diag_printf("%s - Can't write byte - page: %x, addr: %d\n", __FUNCTION__, page, i);
+            return;
+        }
+        // Give device time to recover
+        CYGACC_CALL_IF_DELAY_US(50000);   // 10ms
+        page_addr += size;
+    }
+#endif
+}
+
+// Interrupt support
+
+void
+hal_platform_IRQ_init(void)
+{
+}
+
+// EOF hal_aux.c
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/src/moab.S
@@ -0,0 +1,276 @@
+##=============================================================================
+##
+##      moab.S
+##
+##      MOAB board hardware setup
+##
+##=============================================================================
+#####ECOSGPLCOPYRIGHTBEGIN####
+## -------------------------------------------
+## This file is part of eCos, the Embedded Configurable Operating System.
+## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
+##
+## eCos is free software; you can redistribute it and/or modify it under
+## the terms of the GNU General Public License as published by the Free
+## Software Foundation; either version 2 or (at your option) any later version.
+##
+## eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+## WARRANTY; without even the implied warranty of MERCHANTABILITY or
+## FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+## for more details.
+##
+## You should have received a copy of the GNU General Public License along
+## with eCos; if not, write to the Free Software Foundation, Inc.,
+## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+##
+## As a special exception, if other files instantiate templates or use macros
+## or inline functions from this file, or you compile this file and link it
+## with other works to produce a work based on this file, this file does not
+## by itself cause the resulting work to be covered by the GNU General Public
+## License. However the source code for this file must still be made available
+## in accordance with section (3) of the GNU General Public License.
+##
+## This exception does not invalidate any other reasons why a work based on
+## this file might be covered by the GNU General Public License.
+##
+## Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+## at http://sources.redhat.com/ecos/ecos-license/
+## -------------------------------------------
+#####ECOSGPLCOPYRIGHTEND####
+##=============================================================================
+#######DESCRIPTIONBEGIN####
+##
+## Author(s):   gthomas
+## Contributors:hmt
+## Date:        2002-07-22
+## Purpose:     MOAB board hardware setup
+## Description: This file contains any code needed to initialize the
+##              hardware on a TAMS MOAB (PowerPC 405GPr) board.
+##
+######DESCRIPTIONEND####
+##
+##=============================================================================
+
+#include <pkgconf/hal.h>
+#include <cyg/hal/arch.inc>		/* register symbols et al */
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS        
+#include <cyg/hal/ppc_regs.h>		/* on-chip resource layout, special */
+
+#------------------------------------------------------------------------------
+
+// No useable LEDs
+#define LED(x)                          
+	
+#------------------------------------------------------------------------------       
+                
+FUNC_START( hal_hardware_init )
+        mflr    r30                        // Save return address
+
+#ifndef CYG_HAL_STARTUP_RAM
+        
+        li      r3,0x00000000              // Make sure nothing is cacheable
+        mticcr  r3
+        mtdccr  r3
+
+        // Force data caches to be totally clean
+        lwi     r3,0
+        lwi     r4,0x8000
+10:     dcbf    0,r3        
+        dccci   0,r3
+        addi    r3,r3,16
+        cmpw    r3,r4
+        bne     10b
+
+        // Basic chip configuration
+#if CYGHWR_HAL_POWERPC_CPU_SPEED == 250        
+        lwi     r3,0x09f8102a
+        lwi     r3,0x09f8502a
+#elif CYGHWR_HAL_POWERPC_CPU_SPEED == 333
+        lwi     r3,0x09f8503a
+#else
+#error "Unsupported board/CPU speed"        
+#endif
+        mtdcr   DCR_CPC0_CR0,r3
+        li      r3,0x00000000
+        mtdcr   DCR_CPC0_CR1,r3
+
+        lwi     r3,0x60606000            // Edge conditioning register
+        mtdcr   DCR_CPC0_ECR,r3
+
+        // GPIO
+        //   GPIO 13 - I - media present
+        //   GPIO 14 - O - main flash ALE
+        //   GPIO 15 - O - main flash CLE
+        //   GPIO 16 - I - watchdog ?
+        //   GPIO 17 - O - NAND CE
+        //   GPIO 24 - O - heartbeat LED
+        lwi     r4,GPIO_OR              // Leave NAND not-selected, heartbeat off
+        lwi     r3,0x00004080
+        stw     r3,0(r4)
+        lwi     r4,GPIO_TCR             // Tri-state control - enables outputs
+        lwi     r3,0x0003C080
+        stw     r3,0(r4)
+        
+        li      r3,DCR_SDRAM0_CFG          // See if SDRAM already configured
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mfdcr   r4,DCR_SDRAM0_CFGDATA
+        lwi     r3,0x80800000
+        and     r4,r4,r3
+        cmpw    r3,r4
+        beq     sdram_ok
+        
+        // DRAM controller
+        li      r3,DCR_SDRAM0_CFG            // Turn off controller to allow changes
+        lwi     r4,0x00000000
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+        li      r3,DCR_SDRAM0_TR
+        lwi     r4,0x010A800E
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+        li      r3,DCR_SDRAM0_RTR
+        lwi     r4,0x05F00000
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+        li      r3,DCR_SDRAM0_B1CR           // Note: non-ascending addresses because
+        lwi     r4,0x00062001                // the low 1/2 of memory fails on some boards
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+        li      r3,DCR_SDRAM0_B0CR
+        lwi     r4,0x02062001
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+        
+        lwi     r4,GPIO_OR                // Turn heartbeat LED on
+        lwi     r3,0x00004000
+        stw     r3,0(r4)
+
+        lwi     r3,0xA000                 // Pause for at least 200us
+        mtctr   r3
+13:     nop
+        bdnz    13b
+        
+        li      r3,DCR_SDRAM0_CFG         // Enable controller
+        lwi     r4,0x80800000
+        mtdcr   DCR_SDRAM0_CFGADDR,r3        
+        mtdcr   DCR_SDRAM0_CFGDATA,r4
+
+sdram_ok:               
+        // Bus controller
+        li      r3,DCR_EBC0_B0AP          // BOOT FLASH at 0xFFExxxxx, R/W
+        lwi     r4,0x7F8FFE80
+        mtdcr   DCR_EBC0_CFGADDR,r3
+        mtdcr   DCR_EBC0_CFGDATA,r4
+        li      r3,DCR_EBC0_B0CR
+        lwi     r4,0xFFE38000
+        mtdcr   DCR_EBC0_CFGADDR,r3
+        mtdcr   DCR_EBC0_CFGDATA,r4
+        li      r3,DCR_EBC0_B1AP          // MAIN FLASH at 0xCxxxxxxx, R/W
+        lwi     r4,0x7F8FFE00
+        mtdcr   DCR_EBC0_CFGADDR,r3
+        mtdcr   DCR_EBC0_CFGDATA,r4
+        li      r3,DCR_EBC0_B1CR
+        lwi     r4,0xC0018000             // 1MB, 8bits [actually only 1 byte!]
+        mtdcr   DCR_EBC0_CFGADDR,r3
+        mtdcr   DCR_EBC0_CFGDATA,r4
+
+        // On-chip memory
+        lwi     r4,0xD0000000            // Instruction/Data at 0xD0XXXXXX..0xD7XXXXXX
+        lwi     r3,0x80000000
+        mtdcr   DCR_OCM0_ISARC,r4
+        mtdcr   DCR_OCM0_DSARC,r4
+        mtdcr   DCR_OCM0_ISCNTL,r3
+        mtdcr   DCR_OCM0_DSCNTL,r3
+        
+        lwi     r4,GPIO_OR              // Turn heartbeat LED off
+        lwi     r3,0x00004080
+        stw     r3,0(r4)
+        
+#endif  // ROM or ROMRAM startup
+        
+        lwi     r3,0x80000001              // DRAM can be cached - instructions only
+        iccci   0,r3
+        mticcr  r3
+        li      r3,0x00000000
+        mtdccr  r3
+
+#ifdef CYG_HAL_STARTUP_ROMRAM
+        // Copy image from ROM to RAM
+        mr      r6,r30
+        lwi     r7,0xFFF80000
+        and     r6,r6,r7
+        subi    r6,r6,4
+        lwi     r7,0-4            // where to copy to
+        lwi     r8,__ram_data_end
+10:     lwzu    r5,4(r6)
+        stwu    r5,4(r7)
+        cmplw   r7,r8
+        bne     10b
+        lwi     r30,_hal_hardware_init_done
+#endif
+        
+        lwi     r4,GPIO_OR              // Turn heartbeat LED on
+        lwi     r3,0x00004000
+        stw     r3,0(r4)
+
+        mtlr    r30             // Restore return address
+	blr
+FUNC_END( hal_hardware_init )
+
+        .globl  _hang
+_hang:   nop
+        b       _hang
+        blr
+
+#if 0        
+        .text
+        .globl  _get_cache_contents
+_get_cache_contents:
+        subi    r3,r3,4
+        li      r4,256
+        mtctr   r4
+        li      r4,0        // Address
+        lwi     r7,0xFFFFFFE0
+        mfspr   r5,SPR_CCR0
+10:     and     r5,r5,r7        // CIS=0,CWS=0 =>  DATA, WAY A
+        mtspr   SPR_CCR0,r5
+        sync
+        isync
+        dcread  r6,0,r4
+        stwu    r6,4(r3)
+        and     r5,r5,r7        // CIS=0,CWS=1 =>  DATA, WAY B
+        ori     r5,r5,0x01
+        mtspr   SPR_CCR0,r5
+        sync
+        isync
+        mfspr   r5,SPR_CCR0
+        dcread  r6,0,r4
+        stwu    r6,4(r3)
+        and     r5,r5,r7        // CIS=1,CWS=0 =>  TAG, WAY A
+        ori     r5,r5,0x10
+        mtspr   SPR_CCR0,r5
+        sync
+        isync
+        dcread  r6,0,r4
+        stwu    r6,4(r3)
+        and     r5,r5,r7        // CIS=1,CWS=1 =>  TAG, WAY B
+        ori     r5,r5,0x11
+        mtspr   SPR_CCR0,r5
+        sync
+        isync
+        dcread  r6,0,r4
+        stwu    r6,4(r3)
+        addi    r4,r4,32
+        bdnz    10b
+        blr
+#endif        
+        
+#ifndef CYG_HAL_STARTUP_RAM
+        .section        ".reset_vector","ax"
+        ba      0xFFF80100
+        .previous
+#endif
+
+#------------------------------------------------------------------------------
+# end of moab.S
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/src/plf_redboot_linux_exec.c
@@ -0,0 +1,77 @@
+//==========================================================================
+//
+//      plf_redboot_linux_boot.c
+//
+//      Platform support for RedBoot command to boot Linux
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: 
+// Date:         2003-08-28
+// Purpose:      
+// Description:  
+//              
+// This code is part of RedBoot (tm).
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <cyg/hal/hal_arch.h>
+#include <cyg/hal/hal_if.h>
+#include <cyg/hal/hal_intr.h>
+#include <cyg/hal/hal_cache.h>
+#include <cyg/hal/ppc_regs.h>
+#include <cyg/hal/redboot_linux_exec.h>
+
+//
+// Export system configuration - used when booting a Linux kernel
+// Note: this function is expected to set up the fields which are
+// platform/variant dependent.  It may also override any of the
+// architecture common fields (like memory layout, etc) as appropriate
+//
+externC void 
+plf_redboot_linux_exec(bd_t *board_info)
+{
+    board_info->bi_intfreq	= CYGHWR_HAL_POWERPC_CPU_SPEED*1000000;
+    board_info->bi_busfreq	= CYGHWR_HAL_POWERPC_MEM_SPEED*1000000;
+}
+
+//=========================================================================
+// EOF plf_redboot_linux_exec.c
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/moab/current/support/make_MOAB_flash.c
@@ -0,0 +1,49 @@
+//
+// This program reads a binary image and packs it into 
+// a proper format, suitable for burning into the boot
+// FLASH device on the MOAB platform.
+//
+// CAUTION! - This program is very "hard-wired" to the
+// current MOAB environment.
+//
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <fcntl.h>
+
+#define BOOT_FLASH_SIZE 0x80000
+unsigned char FLASH_image[BOOT_FLASH_SIZE];
+unsigned char BRA_0xFFF80100[] = { 0x4B, 0xF8, 0x01, 0x02 };
+
+int main(int argc, char *argv[])
+{
+    int raw_fd, packed_fd, raw_len;
+
+    if (argc != 3) {
+        fprintf(stderr, "Usage: %s <RAW-binary> <PACKED-binary>\n", argv[0]);
+        exit(1);
+    }
+
+    if ((raw_fd = open(argv[1], O_RDONLY)) < 0) {
+        fprintf(stderr, "Can't open RAW file '%s': %s\n", argv[1], strerror(errno));
+        exit(2);
+    }
+    memset(FLASH_image, 0xFF, sizeof(FLASH_image));
+    if ((raw_len = read(raw_fd, FLASH_image, sizeof(FLASH_image))) < 0) {
+        fprintf(stderr, "Can't read RAW file '%s': %s\n", argv[1], strerror(errno));
+        exit(2);
+    }        
+    memcpy(&FLASH_image[BOOT_FLASH_SIZE-4], BRA_0xFFF80100, sizeof(BRA_0xFFF80100));
+    close(raw_fd);
+
+    if ((packed_fd = open(argv[2], O_RDWR | O_CREAT, 0666)) < 0) {
+        fprintf(stderr, "Can't create '%s': %s\n", argv[2], strerror(errno));
+        exit(3);
+    }
+    if (write(packed_fd, FLASH_image, sizeof(FLASH_image)) != sizeof(FLASH_image)) {
+        fprintf(stderr, "Can't write '%s': %s\n", argv[2], strerror(errno));
+        exit(3);
+    }
+    close(packed_fd);
+}
--- a/packages/hal/powerpc/ppc40x/current/ChangeLog
+++ b/packages/hal/powerpc/ppc40x/current/ChangeLog
@@ -1,3 +1,29 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/ppc405_pci.c: New file - basic support for PCI on PPC 405GP
+
+	* src/hal_diag.c: New file - diagnostic I/O support (previously
+	was defined by platforms).  Note: only for 405GP based devices.
+
+2002-11-21  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/var_intr.c: 
+	* include/variant.inc: 
+	* include/var_intr.h: Better variant/platform support (platforms can
+	override most all default behaviour).
+
+2002-11-20  Gary Thomas  <gary@mlbassoc.com>
+
+	* include/var_cache.h: Cache sizes differ based on CPU.
+
+	* include/var_intr.h: 
+	* include/var_regs.h:
+	* src/var_intr.c: Split interrupt control based on CPU type since
+	403 uses a different controller than the 405 family.
+
+	* cdl/hal_powerpc_ppc40x.cdl: Add 403/405/405GP controls.  Also,
+	enable ROM monitor support (GDB).
+
 2002-05-22  Jesper Skov  <jskov@redhat.com>
 
 	* src/var_intr.c: Fixed warning.
@@ -66,6 +92,7 @@ 2000-11-04  Gary Thomas  <gthomas@redhat
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
--- a/packages/hal/powerpc/ppc40x/current/cdl/hal_powerpc_ppc40x.cdl
+++ b/packages/hal/powerpc/ppc40x/current/cdl/hal_powerpc_ppc40x.cdl
@@ -9,6 +9,7 @@
 ## -------------------------------------------
 ## This file is part of eCos, the Embedded Configurable Operating System.
 ## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
 ##
 ## eCos is free software; you can redistribute it and/or modify it under
 ## the terms of the GNU General Public License as published by the Free
@@ -63,14 +64,20 @@ cdl_package CYGPKG_HAL_POWERPC_PPC40x {
     define_proc {
         puts $cdl_header "#define CYGHWR_HAL_VSR_TABLE (CYGHWR_HAL_POWERPC_VECTOR_BASE + 0x3000)"
         puts $cdl_header "#define CYGHWR_HAL_VIRTUAL_VECTOR_TABLE (CYGHWR_HAL_VSR_TABLE + 0x200)"
+        puts $::cdl_system_header "#define CYGBLD_HAL_VAR_IO_H   <cyg/hal/var_io.h>"
     }
 
-    cdl_component CYGPKG_HAL_POWERPC_PPC403 {
-        display       "PowerPC 403 microprocessor"
-        default_value 1
+    cdl_component CYGHWR_HAL_POWERPC_PPC4XX {
+        display       "PowerPC 4xx microprocessor family"
+        flavor        data
+	legal_values  { "403" "405" "405GP" }
+        default_value { "405GP" }
         implements    CYGINT_HAL_POWERPC_VARIANT
         description "
-            The PowerPC 403 microprocessor."
+            The PowerPC 4xx microprocessor family. These are embedded parts 
+            that in addition to the PowerPC processor core have built in peripherals
+            such as memory controllers, DMA controllers, serial ports and
+            timers/counters."               
 
         cdl_option CYGHWR_HAL_POWERPC_FPU {
             display    "Variant FPU support"
@@ -81,6 +88,104 @@ cdl_package CYGPKG_HAL_POWERPC_PPC40x {
             display    "CPU Variant big-endian"
             calculated 1
         }
+
+    }
+
+    cdl_component CYGHWR_HAL_POWERPC_PPC405_PCI {
+        display       "PCI support"
+        requires      { (CYGHWR_HAL_POWERPC_PPC4XX == "405GP") }
+        active_if     CYGPKG_IO_PCI
+        description   "Variant PCI support - only for 405GP"
+        default_value 1
+        compile       ppc405_pci.c
+    }
+
+    cdl_component CYGHWR_HAL_POWERPC_PPC405_IO {
+        display       "Misc I/O support, including diagnostic serial ports"
+        active_if     { (CYGHWR_HAL_POWERPC_PPC4XX == "405GP") }
+        description   "Variant I/O support - only for 405GP"
+        default_value 1
+        compile       hal_diag.c 
+
+       cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS {
+           display      "Number of communication channels on the board"
+           flavor       data
+           default_value 2+CYGNUM_HAL_PLF_VIRTUAL_VECTOR_COMM_CHANNELS
+       }
+    
+       cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL {
+           display          "Debug serial port"
+           active_if        CYGPRI_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL_CONFIGURABLE
+           flavor data
+           legal_values     0 to CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS-1
+           default_value    0
+           description      "
+               The PPC405GP supports multiple serial ports. Additionally,
+               a platform may define other 'console' devices. This option
+               chooses which port will be used to connect to a host
+               running GDB."
+        }
+    
+        cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL {
+            display          "Diagnostic serial port"
+            active_if        CYGPRI_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_CONFIGURABLE
+            flavor data
+            legal_values     0 to CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS-1
+            default_value    0
+            description      "
+               This option chooses which console port will be used for diagnostic output."
+        }
+    
+        cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD {
+            display       "Baud rate for the HAL diagnostic port"
+            flavor        data
+            legal_values  { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600
+                          4800 7200 9600 14400 19200 38400 57600 115200 230400
+            }
+            default_value 38400
+            description   "
+                This option specifies the default baud rate (speed) for the 
+                HAL diagnostic port."
+        }
+    
+        # This option is only used when USE_ROM_MONITOR is enabled - but
+        # it cannot be a sub-option to that option, since the code uses the
+        # definition in a preprocessor comparison.
+        cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_ROM_DEBUG_CHANNEL {
+            display          "Debug serial port used by ROM monitor"
+            flavor data
+            legal_values     0 to CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS-1
+            default_value    0
+            description      "
+                This option tells the code which console port is in use by 
+                the ROM monitor. It should only be necessary to change this
+                option if a non-standard configurated eCos GDB stub is
+                used."
+        }
+    }
+
+    # Real-time clock/counter specifics
+    cdl_component CYGNUM_HAL_RTC_CONSTANTS {
+        display       "Real-time clock constants."
+        description   "
+            Period is busclock/100."
+        flavor        none
+    
+        cdl_option CYGNUM_HAL_RTC_NUMERATOR {
+            display       "Real-time clock numerator"
+            flavor        data
+            calculated    1000000000
+        }
+        cdl_option CYGNUM_HAL_RTC_DENOMINATOR {
+            display       "Real-time clock denominator"
+            flavor        data
+            calculated    100
+        }
+        cdl_option CYGNUM_HAL_RTC_PERIOD {
+            display       "Real-time clock period"
+            flavor        data
+            calculated    { (((CYGHWR_HAL_POWERPC_CPU_SPEED*4*1000000)/16)/100) }
+        }
     }
 
     define_proc {
@@ -93,5 +198,23 @@ cdl_package CYGPKG_HAL_POWERPC_PPC40x {
         no_define
     }
 
+    cdl_option CYGSEM_HAL_USE_ROM_MONITOR {
+        display       "Work with a ROM monitor"
+        flavor        bool
+        default_value { (CYG_HAL_STARTUP == "RAM" &&
+                        !CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS &&
+                        !CYGINT_HAL_USE_ROM_MONITOR_UNSUPPORTED &&
+                        !CYGSEM_HAL_POWERPC_COPY_VECTORS) ? 1 : 0 }
+        parent        CYGPKG_HAL_ROM_MONITOR
+        requires      { CYG_HAL_STARTUP == "RAM" }
+        requires      ! CYGSEM_HAL_POWERPC_COPY_VECTORS
+        requires      ! CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
+        requires      ! CYGINT_HAL_USE_ROM_MONITOR_UNSUPPORTED
+        description   "
+            Allow coexistence with ROM monitor (RedBoot or GDB stubs) by
+            only initializing interrupt vectors on startup, thus leaving
+            exception handling to the ROM monitor."
+    }
+
     compile       var_intr.c var_misc.c variant.S
 }
--- a/packages/hal/powerpc/ppc40x/current/include/var_cache.h
+++ b/packages/hal/powerpc/ppc40x/current/include/var_cache.h
@@ -11,6 +11,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -67,6 +68,7 @@
 //-----------------------------------------------------------------------------
 // Cache dimensions
 
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)
 // Data cache
 #define HAL_DCACHE_SIZE                 8192    // Size of data cache in bytes
 #define HAL_DCACHE_LINE_SIZE            16      // Size of a data cache line
@@ -76,6 +78,19 @@
 #define HAL_ICACHE_SIZE                 16384   // Size of cache in bytes
 #define HAL_ICACHE_LINE_SIZE            16      // Size of a cache line
 #define HAL_ICACHE_WAYS                 2       // Associativity of the cache
+#endif  // 403
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+// Data cache
+#define HAL_DCACHE_SIZE                 (16*1024) // Size of data cache in bytes
+#define HAL_DCACHE_LINE_SIZE            32        // Size of a data cache line
+#define HAL_DCACHE_WAYS                 2         // Associativity of the cache
+
+// Instruction cache
+#define HAL_ICACHE_SIZE                 (16*1024) // Size of cache in bytes
+#define HAL_ICACHE_LINE_SIZE            32        // Size of a cache line
+#define HAL_ICACHE_WAYS                 2         // Associativity of the cache
+#endif // 405
 
 #define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
 #define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
@@ -96,13 +111,13 @@
     _indx_ = 0;                                                 \
     _ix_ = HAL_DCACHE_SIZE/2;                                   \
     for (_i_ = 0;  _i_ < HAL_DCACHE_SETS;  _i_++) {             \
-/*        asm volatile ("dcbf 0,%0;" :: "r"(_indx_));           */  \
-/*        asm volatile ("dcbf %1,%0;" :: "r"(_indx_), "r"(_ix_)); */\
-        asm volatile ("dccci 0,%0;" :: "r"(_indx_));            \
+        asm volatile ("dccci 0,%0;" :: "r"(_indx_));             \
+        asm volatile ("dccci %1,%0;" :: "r"(_indx_), "r"(_ix_)); \
         _indx_ += HAL_DCACHE_LINE_SIZE;                         \
     }                                                           \
     CYG_MACRO_END
 
+#if 0
 // Synchronize the contents of the cache with memory.                                   
 #define HAL_DCACHE_SYNC()                                                               \
     CYG_MACRO_START                                                                     \
@@ -111,6 +126,18 @@
         asm volatile ("dcbf 0,%0;" :: "r"(_indx_));                                     \
     }                                                                                   \
     CYG_MACRO_END
+#else
+// Synchronize the contents of the cache with memory.
+#define HAL_DCACHE_SYNC()                                                     \
+    CYG_MACRO_START                                                           \
+    cyg_int32 i;                                                              \
+    cyg_uint32 *__base = (cyg_uint32 *) (0);                  \
+/*    for (i = 0;  i < HAL_DCACHE_SIZE;  i += sizeof(cyg_uint32)) {      */ \
+    for (i = 0; i < (HAL_DCACHE_SIZE/HAL_DCACHE_LINE_SIZE); i++, __base += HAL_DCACHE_LINE_SIZE/4){\
+        asm volatile ("lwz %%r0,0(%0)" : : "r" (__base) : "r0");      \
+    }                                                                         \
+    CYG_MACRO_END
+#endif
 
 // Query the state of the data cache
 #define HAL_DCACHE_IS_ENABLED(_state_)          \
@@ -146,24 +173,78 @@
 
 // Write dirty cache lines to memory and invalidate the cache entries
 // for the given address range.
-//#define HAL_DCACHE_FLUSH( _base_ , _size_ )
-
+#define HAL_DCACHE_FLUSH( _base_ , _size_ )                     \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbf 0,%0;sync;" : : "r" (__base));      \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
+   
 // Invalidate cache lines in the given range without writing to memory.
-//#define HAL_DCACHE_INVALIDATE( _base_ , _size_ )
+#define HAL_DCACHE_INVALIDATE( _base_ , _size_ )                \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbi 0,%0;sync;" : : "r" (__base));      \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
 
 // Write dirty cache lines to memory for the given address range.
-//#define HAL_DCACHE_STORE( _base_ , _size_ )
+#define HAL_DCACHE_STORE( _base_ , _size_ )                     \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbst 0,%0;sync;" : : "r" (__base));     \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
 
 // Preread the given range into the cache with the intention of reading
 // from it later.
-//#define HAL_DCACHE_READ_HINT( _base_ , _size_ )
+#define HAL_DCACHE_READ_HINT( _base_ , _size_ )                 \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbt 0,%0;" : : "r" (__base));           \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
 
 // Preread the given range into the cache with the intention of writing
 // to it later.
-//#define HAL_DCACHE_WRITE_HINT( _base_ , _size_ )
+#define HAL_DCACHE_WRITE_HINT( _base_ , _size_ )                \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbtst 0,%0;" : : "r" (__base));         \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
 
 // Allocate and zero the cache lines associated with the given range.
-//#define HAL_DCACHE_ZERO( _base_ , _size_ )
+#define HAL_DCACHE_ZERO( _base_ , _size_ )                      \
+    CYG_MACRO_START                                             \
+    cyg_uint32 __base = (cyg_uint32) (_base_);                  \
+    cyg_int32 __size = (cyg_int32) (_size_);                    \
+    while (__size > 0) {                                        \
+        asm volatile ("dcbz 0,%0;" : : "r" (__base));           \
+        __base += HAL_DCACHE_LINE_SIZE;                         \
+        __size -= HAL_DCACHE_LINE_SIZE;                         \
+    }                                                           \
+    CYG_MACRO_END
 
 //-----------------------------------------------------------------------------
 // Global control of Instruction cache
@@ -213,6 +294,13 @@
 // Invalidate cache lines in the given range without writing to memory.
 //#define HAL_ICACHE_INVALIDATE( _base_ , _size_ )
 
+#ifdef CYGHWR_HAL_POWERPC_ENABLE_MMU
+// Map a RAM address to a non-cached mirror
+#define CYGARC_UNCACHED_ADDRESS(p) ((unsigned long)(p) | 0x80000000)
+#else
+#define CYGARC_UNCACHED_ADDRESS(p) (p)
+#endif
+
 //-----------------------------------------------------------------------------
 #endif // ifndef CYGONCE_VAR_CACHE_H
 // End of var_cache.h
--- a/packages/hal/powerpc/ppc40x/current/include/var_intr.h
+++ b/packages/hal/powerpc/ppc40x/current/include/var_intr.h
@@ -11,6 +11,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -74,24 +75,73 @@
 
 #define CYGHWR_HAL_INTERRUPT_CONTROLLER_ACCESS_DEFINED
 
-// Additional interrupt sources which are supported by the 40x
-#define CYGNUM_HAL_INTERRUPT_CRITICAL         2
-#define CYGNUM_HAL_INTERRUPT_SERIAL_RCV       3
-#define CYGNUM_HAL_INTERRUPT_SERIAL_XMT       4
-#define CYGNUM_HAL_INTERRUPT_JTAG_RCV         5
-#define CYGNUM_HAL_INTERRUPT_JTAG_XMT         6
-#define CYGNUM_HAL_INTERRUPT_DMA0             7
-#define CYGNUM_HAL_INTERRUPT_DMA1             8
-#define CYGNUM_HAL_INTERRUPT_DMA2             9
-#define CYGNUM_HAL_INTERRUPT_DMA3            10
-#define CYGNUM_HAL_INTERRUPT_EXT0            11
-#define CYGNUM_HAL_INTERRUPT_EXT1            12
-#define CYGNUM_HAL_INTERRUPT_EXT2            13
-#define CYGNUM_HAL_INTERRUPT_EXT3            14
-#define CYGNUM_HAL_INTERRUPT_EXT4            15
-#define CYGNUM_HAL_INTERRUPT_VAR_TIMER       16
-#define CYGNUM_HAL_INTERRUPT_FIXED_TIMER     17
-#define CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER  18
+//--------------------------------------------------------------------------
+// Interrupt layout - differs by chip model (interrupt controller)
+
+#ifndef CYGHWR_HAL_INTERRUPT_LAYOUT_DEFINED
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)
+// Additional interrupt sources which are supported by the 403
+#define CYGNUM_HAL_INTERRUPT_403_BASE        2
+#define CYGNUM_HAL_INTERRUPT_first           CYGNUM_HAL_INTERRUPT_403_BASE
+#define CYGNUM_HAL_INTERRUPT_CRITICAL        (CYGNUM_HAL_INTERRUPT_403_BASE+0)
+#define CYGNUM_HAL_INTERRUPT_SERIAL_RCV      (CYGNUM_HAL_INTERRUPT_403_BASE+1)
+#define CYGNUM_HAL_INTERRUPT_SERIAL_XMT      (CYGNUM_HAL_INTERRUPT_403_BASE+2) 
+#define CYGNUM_HAL_INTERRUPT_JTAG_RCV        (CYGNUM_HAL_INTERRUPT_403_BASE+3)
+#define CYGNUM_HAL_INTERRUPT_JTAG_XMT        (CYGNUM_HAL_INTERRUPT_403_BASE+4)
+#define CYGNUM_HAL_INTERRUPT_DMA0            (CYGNUM_HAL_INTERRUPT_403_BASE+5)
+#define CYGNUM_HAL_INTERRUPT_DMA1            (CYGNUM_HAL_INTERRUPT_403_BASE+6)
+#define CYGNUM_HAL_INTERRUPT_DMA2            (CYGNUM_HAL_INTERRUPT_403_BASE+7)
+#define CYGNUM_HAL_INTERRUPT_DMA3            (CYGNUM_HAL_INTERRUPT_403_BASE+8)
+#define CYGNUM_HAL_INTERRUPT_EXT0            (CYGNUM_HAL_INTERRUPT_403_BASE+9)
+#define CYGNUM_HAL_INTERRUPT_EXT1            (CYGNUM_HAL_INTERRUPT_403_BASE+10)
+#define CYGNUM_HAL_INTERRUPT_EXT2            (CYGNUM_HAL_INTERRUPT_403_BASE+11)
+#define CYGNUM_HAL_INTERRUPT_EXT3            (CYGNUM_HAL_INTERRUPT_403_BASE+12)
+#define CYGNUM_HAL_INTERRUPT_EXT4            (CYGNUM_HAL_INTERRUPT_403_BASE+13)
+#define CYGNUM_HAL_INTERRUPT_last            CYGNUM_HAL_INTERRUPT_EXT4
+#endif // CYGHWR_HAL_POWERPC_PPC4XX_403
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+// Additional interrupt sources which are supported by the 405
+#define CYGNUM_HAL_INTERRUPT_405_BASE        2
+#define CYGNUM_HAL_INTERRUPT_first           CYGNUM_HAL_INTERRUPT_405_BASE
+#define CYGNUM_HAL_INTERRUPT_UART0           (CYGNUM_HAL_INTERRUPT_405_BASE+0)
+#define CYGNUM_HAL_INTERRUPT_UART1           (CYGNUM_HAL_INTERRUPT_405_BASE+1)
+#define CYGNUM_HAL_INTERRUPT_IIC             (CYGNUM_HAL_INTERRUPT_405_BASE+2)
+#define CYGNUM_HAL_INTERRUPT_PCI             (CYGNUM_HAL_INTERRUPT_405_BASE+4)
+#define CYGNUM_HAL_INTERRUPT_DMA0            (CYGNUM_HAL_INTERRUPT_405_BASE+5)
+#define CYGNUM_HAL_INTERRUPT_DMA1            (CYGNUM_HAL_INTERRUPT_405_BASE+6)
+#define CYGNUM_HAL_INTERRUPT_DMA2            (CYGNUM_HAL_INTERRUPT_405_BASE+7)
+#define CYGNUM_HAL_INTERRUPT_DMA3            (CYGNUM_HAL_INTERRUPT_405_BASE+8)
+#define CYGNUM_HAL_INTERRUPT_EXT_WAKE        (CYGNUM_HAL_INTERRUPT_405_BASE+9)
+#define CYGNUM_HAL_INTERRUPT_MAL_SERR        (CYGNUM_HAL_INTERRUPT_405_BASE+10)
+#define CYGNUM_HAL_INTERRUPT_MAL_TX_EOB      (CYGNUM_HAL_INTERRUPT_405_BASE+11)
+#define CYGNUM_HAL_INTERRUPT_MAL_RX_EOB      (CYGNUM_HAL_INTERRUPT_405_BASE+12)
+#define CYGNUM_HAL_INTERRUPT_MAL_TX_DE       (CYGNUM_HAL_INTERRUPT_405_BASE+13)
+#define CYGNUM_HAL_INTERRUPT_MAL_RX_DE       (CYGNUM_HAL_INTERRUPT_405_BASE+14)
+#define CYGNUM_HAL_INTERRUPT_EMAC0           (CYGNUM_HAL_INTERRUPT_405_BASE+15)
+#define CYGNUM_HAL_INTERRUPT_PCI_SERR        (CYGNUM_HAL_INTERRUPT_405_BASE+16)
+#define CYGNUM_HAL_INTERRUPT_EMAC1           (CYGNUM_HAL_INTERRUPT_405_BASE+17)
+#define CYGNUM_HAL_INTERRUPT_PCI_PM          (CYGNUM_HAL_INTERRUPT_405_BASE+18)
+#define CYGNUM_HAL_INTERRUPT_GPT0            (CYGNUM_HAL_INTERRUPT_405_BASE+19)
+#define CYGNUM_HAL_INTERRUPT_GPT1            (CYGNUM_HAL_INTERRUPT_405_BASE+20)
+#define CYGNUM_HAL_INTERRUPT_GPT2            (CYGNUM_HAL_INTERRUPT_405_BASE+21)
+#define CYGNUM_HAL_INTERRUPT_GPT3            (CYGNUM_HAL_INTERRUPT_405_BASE+22)
+#define CYGNUM_HAL_INTERRUPT_GPT4            (CYGNUM_HAL_INTERRUPT_405_BASE+23)
+#define CYGNUM_HAL_INTERRUPT_IRQ0            (CYGNUM_HAL_INTERRUPT_405_BASE+25)
+#define CYGNUM_HAL_INTERRUPT_IRQ1            (CYGNUM_HAL_INTERRUPT_405_BASE+26)
+#define CYGNUM_HAL_INTERRUPT_IRQ2            (CYGNUM_HAL_INTERRUPT_405_BASE+27)
+#define CYGNUM_HAL_INTERRUPT_IRQ3            (CYGNUM_HAL_INTERRUPT_405_BASE+28)
+#define CYGNUM_HAL_INTERRUPT_IRQ4            (CYGNUM_HAL_INTERRUPT_405_BASE+29)
+#define CYGNUM_HAL_INTERRUPT_IRQ5            (CYGNUM_HAL_INTERRUPT_405_BASE+30)
+#define CYGNUM_HAL_INTERRUPT_IRQ6            (CYGNUM_HAL_INTERRUPT_405_BASE+31)
+#define CYGNUM_HAL_INTERRUPT_last            CYGNUM_HAL_INTERRUPT_IRQ6
+#endif // CYGHWR_HAL_POWERPC_PPC4XX_405
+#endif // CYGHWR_HAL_INTERRUPT_LAYOUT_DEFINED
+
+// These are faked - not part of the interrupt controller itself
+#define CYGNUM_HAL_INTERRUPT_VAR_TIMER       (CYGNUM_HAL_INTERRUPT_last+1)
+#define CYGNUM_HAL_INTERRUPT_FIXED_TIMER     (CYGNUM_HAL_INTERRUPT_last+2)
+#define CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER  (CYGNUM_HAL_INTERRUPT_last+3)
 
 #define CYGNUM_HAL_ISR_MAX                   CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER
 
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/ppc40x/current/include/var_io.h
@@ -0,0 +1,180 @@
+#ifndef CYGONCE_HAL_VAR_IO_H
+#define CYGONCE_HAL_VAR_IO_H
+
+//==========================================================================
+//
+//      var_io.h
+//
+//      PowerPC 40x variant I/O support
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    jskov
+// Contributors: jskov,gthomas
+// Date:         2000-08-27
+// Purpose:      Provide PPC40x I/O functions
+// Description:  
+// Usage:        Included via the architecture register header:
+//               #include <cyg/hal/hal_io.h>
+//               ...
+//              
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include CYGBLD_HAL_PLF_IO_H
+
+#ifdef CYGPKG_IO_PCI
+// These must be defined by the platform
+#if !defined(CYG_PCI_MAX_BUS)
+#error "Missing CYG_PCI_MAX_BUS platform definition"
+#endif
+#if !defined(CYG_PCI_MIN_DEV)
+#error "Missing CYG_PCI_MIN_DEV platform definition"
+#endif
+#if !defined(CYG_PCI_MAX_DEV)
+#error "Missing CYG_PCI_MAX_DEV platform definition"
+#endif
+#if !defined(HAL_PCI_ALLOC_BASE_MEMORY)
+#error "Missing HAL_PCI_ALLOC_BASE_MEMORY platform definition"
+#endif
+#if !defined(HAL_PCI_ALLOC_BASE_IO)
+#error "Missing HAL_PCI_ALLOC_BASE_IO platform definition"
+#endif
+#if !defined(HAL_PCI_PHYSICAL_MEMORY_BASE)
+#error "Missing HAL_PCI_PHYSICAL_MEMORY_BASE platform definition"
+#endif
+#if !defined(HAL_PCI_PHYSICAL_IO_BASE)
+#error "Missing HAL_PCI_PHYSICAL_IO_BASE platform definition"
+#endif
+//#if !defined(CYGMEM_SECTION_pci_window)
+//#error "Missing CYGMEM_SECTION_pci_window platform definition"
+//#endif
+//#if !defined(CYGMEM_SECTION_pci_window_SIZE)
+//#error "Missing CYGMEM_SECTION_pci_window_SIZE platform definition"
+//#endif
+
+// Initialize the PCI environment
+externC void hal_ppc405_pci_init(void);
+#define HAL_PCI_INIT() \
+  hal_ppc405_pci_init()
+
+// Translate the PCI interrupt requested by the device (INTA#, INTB#,
+// INTC# or INTD#) to the associated CPU interrupt (i.e., HAL vector).
+externC void hal_ppc405_pci_translate_interrupt(int bus, int devfn, int *vec, int *valid);
+#define HAL_PCI_TRANSLATE_INTERRUPT( __bus, __devfn, __vec, __valid) \
+  hal_ppc405_pci_translate_interrupt(__bus, __devfn, &__vec, &__valid)
+
+// Read a value from the PCI configuration space of the appropriate
+// size at an address composed from the bus, devfn and offset.
+externC cyg_uint8 hal_ppc405_pci_cfg_read_uint8(int bus, int dev, int offset);
+#define HAL_PCI_CFG_READ_UINT8( __bus, __devfn, __offset, __val )  \
+  __val = hal_ppc405_pci_cfg_read_uint8(__bus, __devfn, __offset)
+    
+externC cyg_uint16 hal_ppc405_pci_cfg_read_uint16(int bus, int dev, int offset);
+#define HAL_PCI_CFG_READ_UINT16( __bus, __devfn, __offset, __val )  \
+  __val = hal_ppc405_pci_cfg_read_uint16(__bus, __devfn, __offset)
+    
+externC cyg_uint32 hal_ppc405_pci_cfg_read_uint32(int bus, int dev, int offset);
+#define HAL_PCI_CFG_READ_UINT32( __bus, __devfn, __offset, __val )  \
+  __val = hal_ppc405_pci_cfg_read_uint32(__bus, __devfn, __offset)
+
+// Write a value to the PCI configuration space of the appropriate
+// size at an address composed from the bus, devfn and offset.
+externC void hal_ppc405_pci_cfg_write_uint8(int bus, int dev, int offset, cyg_uint8 val);
+#define HAL_PCI_CFG_WRITE_UINT8( __bus, __devfn, __offset, __val ) \
+  hal_ppc405_pci_cfg_write_uint8(__bus, __devfn, __offset, __val)
+
+externC void hal_ppc405_pci_cfg_write_uint16(int bus, int dev, int offset, cyg_uint16 val);
+#define HAL_PCI_CFG_WRITE_UINT16( __bus, __devfn, __offset, __val ) \
+  hal_ppc405_pci_cfg_write_uint16(__bus, __devfn, __offset, __val)
+
+externC void hal_ppc405_pci_cfg_write_uint32(int bus, int dev, int offset, cyg_uint32 val);
+#define HAL_PCI_CFG_WRITE_UINT32( __bus, __devfn, __offset, __val ) \
+  hal_ppc405_pci_cfg_write_uint32(__bus, __devfn, __offset, __val)
+#endif // CYGPKG_IO_PCI
+
+static __inline__ unsigned long
+_le32(unsigned long val)
+{
+    return (((val & 0x000000FF) << 24) |
+            ((val & 0x0000FF00) <<  8) |
+            ((val & 0x00FF0000) >>  8) |
+            ((val & 0xFF000000) >> 24));
+}
+
+static __inline__ unsigned short
+_le16(unsigned short val)
+{
+    return (((val & 0x000000FF) << 8) |
+            ((val & 0x0000FF00) >> 8));
+}
+
+#define HAL_WRITE_UINT32LE(_addr_, _val_) \
+  HAL_WRITE_UINT32(_addr_, _le32(_val_))
+#define HAL_WRITE_UINT16LE(_addr_, _val_) \
+  HAL_WRITE_UINT16(_addr_, _le16(_val_))
+#define HAL_WRITE_UINT8LE(_addr_, _val_) \
+  HAL_WRITE_UINT8(_addr_, _val_)
+#define HAL_READ_UINT32LE(_addr_, _val_)        \
+  {                                             \
+      HAL_READ_UINT32(_addr_, _val_);           \
+      _val_ = _le32(_val_);                     \
+  }
+#define HAL_READ_UINT16LE(_addr_, _val_)        \
+  {                                             \
+      HAL_READ_UINT16(_addr_, _val_);           \
+      _val_ = _le16(_val_);                     \
+  }
+#define HAL_READ_UINT8LE(_addr_, _val_)        \
+  HAL_READ_UINT8(_addr_, _val_)
+
+//-----------------------------------------------------------------------------
+// Additional functions exported by HAL (no good place to define them!)
+//
+#if !defined(__ASSEMBLER__)
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+externC bool hal_ppc405_i2c_put_bytes(int addr, cyg_uint8 *val, int len);
+externC bool hal_ppc405_i2c_get_bytes(int addr, cyg_uint8 *val, int len);
+#endif
+#endif
+
+//-----------------------------------------------------------------------------
+#endif // ifdef CYGONCE_HAL_VAR_IO_H
+// End of var_io.h
--- a/packages/hal/powerpc/ppc40x/current/include/var_regs.h
+++ b/packages/hal/powerpc/ppc40x/current/include/var_regs.h
@@ -12,6 +12,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -48,9 +49,9 @@
 // Date:         2000-08-27
 // Purpose:      Provide PPC40x register definitions
 // Description:  Provide PPC40x register definitions
-//               The short difinitions (sans CYGARC_REG_) are exported only
+//               The short definitions (sans CYGARC_REG_) are exported only
 //               if CYGARC_HAL_COMMON_EXPORT_CPU_MACROS is defined.
-// Usage:        Included via the acrhitecture register header:
+// Usage:        Included via the architecture register header:
 //               #include <cyg/hal/ppc_regs.h>
 //               ...
 //              
@@ -59,8 +60,10 @@
 //
 //==========================================================================
 
+#include <cyg/hal/plf_regs.h>
+
 //--------------------------------------------------------------------------
-// Cache
+// Hardware control (usage depends on chip model)
 #define CYGARC_REG_HID0   1008
 
 #ifdef CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
@@ -71,8 +74,10 @@
 // MMU control.
 #ifdef CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
 
+#define SPR_ESR         980            // Exception syndrome
 #define SPR_EVPR        982            // Exception vector prefix
 #define SPR_PID         945            // Process ID
+#define SPR_CCR0        0x3B3          // Core configuration register
 
 #define M_EPN_EPNMASK  0xfffff000      // effective page no mask
 #define M_EPN_EV       0x00000040      // entry valid
@@ -96,17 +101,179 @@
 
 //--------------------------------------------------------------------------
 // Device control register access macros.
-#define CYGARC_MTDCR(_tbr_, _v_) \
-    asm volatile ("mtdcr %0, %1;" :: "I" (_tbr_), "r" (_v_));
-#define CYGARC_MFDCR(_tbr_, _v_) \
-    asm volatile ("mfdcr %0, %1;" : "=r" (_v_) : "I" (_tbr_));
+#define CYGARC_MTDCR(_dcr_, _v_) \
+    asm volatile ("mtdcr %0, %1;" :: "I" (_dcr_), "r" (_v_));
+#define CYGARC_MFDCR(_dcr_, _v_) \
+    asm volatile ("mfdcr %0, %1;" : "=r" (_v_) : "I" (_dcr_));
 
 #ifdef CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
 
 // Interrupt control (device) registers
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)
 #define DCR_EXIER  66
 #define DCR_EXISR  64
 #define DCR_IOCR   160
+#endif
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+// Interrupt controller
+#define DCR_UIC0_SR   0xC0  // Status register
+#define DCR_UIC0_ER   0xC2  // Enable register
+#define DCR_UIC0_CR   0xC3  // Critical [or not]
+#define DCR_UIC0_PR   0xC4  // Polarity (high/low)
+#define DCR_UIC0_TR   0xC5  // Trigger (level/edge)
+#define DCR_UIC0_MSR  0xC6  // Masked status
+#define DCR_UIC0_VR   0xC7  // Vector
+#define DCR_UIC0_VCR  0xC8  // Vector configuration
+
+// PPC 405GP control registers (in DCR space)
+#define DCR_SDRAM0_CFGADDR   0x10
+#define DCR_SDRAM0_CFGDATA   0x11
+#define DCR_EBC0_CFGADDR     0x12
+#define DCR_EBC0_CFGDATA     0x13
+#define DCR_CPC0_CR0         0xB1
+#define DCR_CPC0_CR1         0xB2
+#define DCR_CPC0_ECR         0xAA
+
+// External bus controller (indirect via EBC0_CFGADDR/EBC0_CFGDATA)
+#define DCR_EBC0_B0CR        0x00
+#define DCR_EBC0_B1CR        0x01
+#define DCR_EBC0_B2CR        0x02
+#define DCR_EBC0_B3CR        0x03
+#define DCR_EBC0_B4CR        0x04
+#define DCR_EBC0_B5CR        0x05
+#define DCR_EBC0_B6CR        0x06
+#define DCR_EBC0_B7CR        0x07
+#define DCR_EBC0_B0AP        0x10
+#define DCR_EBC0_B1AP        0x11
+#define DCR_EBC0_B2AP        0x12
+#define DCR_EBC0_B3AP        0x13
+#define DCR_EBC0_B4AP        0x14
+#define DCR_EBC0_B5AP        0x15
+#define DCR_EBC0_B6AP        0x16
+#define DCR_EBC0_B7AP        0x17
+#define DCR_EBC0_BEAR        0x20
+#define DCR_EBC0_BESR0       0x21
+#define DCR_EBC0_BESR1       0x22
+#define DCR_EBC0_CFG         0x23
+
+// SDRAM controller
+#define DCR_SDRAM0_CFG       0x20     // Memory controller options
+#define DCR_SDRAM0_STATUS    0x24     // Controller status
+#define DCR_SDRAM0_RTR       0x30     // Refresh timer
+#define DCR_SDRAM0_PMIT      0x34     // Power management idle timer
+#define DCR_SDRAM0_B0CR      0x40     // Bank 0 configuration
+#define DCR_SDRAM0_B1CR      0x44     // Bank 1 configuration
+#define DCR_SDRAM0_TR        0x80     // Timing
+
+// On-chip memory
+#define DCR_OCM0_ISARC       0x18     // Instruction side address compare
+#define DCR_OCM0_ISCNTL      0x19     // Instruction side control
+#define DCR_OCM0_DSARC       0x1A     // Data side address compare
+#define DCR_OCM0_DSCNTL      0x1B     // Data side control
+
+// I2C controller
+#define IIC0_MDBUF           (_PPC405GP_IIC0+0x00)  // Master data buffer
+#define IIC0_SDBUF           (_PPC405GP_IIC0+0x02)  // Slave data buffer
+#define IIC0_LMADR           (_PPC405GP_IIC0+0x04)  // Master address (low)
+#define IIC0_HMADR           (_PPC405GP_IIC0+0x05)  // Master address (high)
+#define IIC0_CNTL            (_PPC405GP_IIC0+0x06)  // Control
+#define IIC0_CNTL_HMT           0x80   // Halt master transfer
+#define IIC0_CNTL_AMD           0x40   // Address mode (0=7 bit, 1=10 bit)
+#define IIC0_CNTL_TCT           0x30   // Transfer size (1-4 bytes)
+#define IIC0_CNTL_TCT_SHIFT         4
+#define IIC0_CNTL_TCT_1             0x00  
+#define IIC0_CNTL_TCT_2             0x10
+#define IIC0_CNTL_TCT_3             0x20
+#define IIC0_CNTL_TCT_4             0x30
+#define IIC0_CNTL_RPST          0x08   // Repeated start
+#define IIC0_CNTL_CHT           0x04   // Chain transfer
+#define IIC0_CNTL_RW            0x02   // Read/write
+#define IIC0_CNTL_RW_READ           0x02
+#define IIC0_CNTL_RW_WRITE          0x00
+#define IIC0_CNTL_PT            0x01   // Pending transfer
+#define IIC0_MDCNTL          (_PPC405GP_IIC0+0x07)  // Mode control
+#define IIC0_MDCNTL_FSDB        0x80   // Flush slave data buffer
+#define IIC0_MDCNTL_FMDB        0x40   // Flush master data buffer
+#define IIC0_MDCNTL_FSM         0x10   // Fast/standard mode (1=fast)
+#define IIC0_MDCNTL_ESM         0x08   // Enable slave mode
+#define IIC0_MDCNTL_EINT        0x04   // Enable interrupt
+#define IIC0_MDCNTL_EUBS        0x02   // Exit unknown bus state
+#define IIC0_MDCNTL_HSCL        0x01   // Hold serial clock low (slave only)
+#define IIC0_STS             (_PPC405GP_IIC0+0x08)  // Status
+#define IIC0_STS_SSS            0x80   // Slave operation in progress
+#define IIC0_STS_SLPR           0x40   // Sleep request
+#define IIC0_STS_MDBS           0x20   // Master data buffer status (0=empty)
+#define IIC0_STS_MDBF           0x10   // Master data buffer status (1=full)
+#define IIC0_STS_SCMP           0x08   // Stop complete
+#define IIC0_STS_ERR            0x04   // Error
+#define IIC0_STS_IRQA           0x02   // Interrupt active
+#define IIC0_STS_PT             0x01   // Transfer pending
+#define IIC0_EXTSTS          (_PPC405GP_IIC0+0x09)  // Extended status
+#define IIC0_EXTSTS_IRQP        0x80   // Interrupt pending
+#define IIC0_EXTSTS_BCS         0x70   // Bus status
+#define IIC0_EXTSTS_BCS_ss          0x10   // Slave selected
+#define IIC0_EXTSTS_BCS_st          0x20   // Slave transfer
+#define IIC0_EXTSTS_BCS_mt          0x30   // Master transfer
+#define IIC0_EXTSTS_BCS_free        0x40   // Bus free
+#define IIC0_EXTSTS_BCS_busy        0x50   // Bus busy
+#define IIC0_EXTSTS_IRQD        0x08   // IRQ on deck 
+#define IIC0_EXTSTS_LA          0x04   // Lost arbitration
+#define IIC0_EXTSTS_ICT         0x02   // Incomplete transfer
+#define IIC0_EXTSTS_XFRA        0x01   // Transfer aborted
+#define IIC0_LSADR           (_PPC405GP_IIC0+0x0A)  // Slave address (low)
+#define IIC0_HSADR           (_PPC405GP_IIC0+0x0B)  // Slave address (high)
+#define IIC0_CLKDIV          (_PPC405GP_IIC0+0x0C)  // Clock divide
+#define IIC0_INTRMSK         (_PPC405GP_IIC0+0x0D)  // Interrupt mask
+#define IIC0_XFRCNT          (_PPC405GP_IIC0+0x0E)  // Transfer count
+#define IIC0_XFRCNT_STC         0x70   // Slave transfer count
+#define IIC0_XFRCNT_STC_SHIFT   4
+#define IIC0_XFRCNT_MTC         0x07   // Master transfer count
+#define IIC0_XFRCNT_MTC_SHIFT   0         
+#define IIC0_XTCNTLSS        (_PPC405GP_IIC0+0x0F)  // Extended control & slave status
+#define IIC0_DIRECT          (_PPC405GP_IIC0+0x10)  // Direct control over I/O lines
+
+// GPIO (General Purpose I/O)
+#define GPIO_OR              (_PPC405GP_GPIO+0x00)  // Output register
+#define GPIO_TCR             (_PPC405GP_GPIO+0x04)  // Tri-state control
+#define GPIO_OSRH            (_PPC405GP_GPIO+0x08)  // Output select (high)
+#define GPIO_OSRL            (_PPC405GP_GPIO+0x0C)  // Output select (low)
+#define GPIO_TSRH            (_PPC405GP_GPIO+0x10)  // Tri-state select (high)
+#define GPIO_TSRL            (_PPC405GP_GPIO+0x14)  // Tri-state select (low)
+#define GPIO_ODR             (_PPC405GP_GPIO+0x18)  // Open drain
+#define GPIO_IR              (_PPC405GP_GPIO+0x1C)  // Input register
+#define GPIO_RR              (_PPC405GP_GPIO+0x20)  // Receive register
+#define GPIO_ISRH            (_PPC405GP_GPIO+0x30)  // Input select (high)
+#define GPIO_ISRL            (_PPC405GP_GPIO+0x34)  // Input select (low)
+
+// PCI
+
+// PCI Bridge
+#define PCIL0_PMM0LA         (_PPC405GP_PCI_BRIDGE+0x00)     // PMM 0 Local address
+#define PCIL0_PMM0MA         (_PPC405GP_PCI_BRIDGE+0x04)     // PMM 0 Mask/Attributes
+#define PCIL0_PMM0PCILA      (_PPC405GP_PCI_BRIDGE+0x08)     // PMM 0 PCI Low Address
+#define PCIL0_PMM0PCIHA      (_PPC405GP_PCI_BRIDGE+0x0C)     // PMM 0 PCI High Address
+#define PCIL0_PMM1LA         (_PPC405GP_PCI_BRIDGE+0x10)     // PMM 1 Local address
+#define PCIL0_PMM1MA         (_PPC405GP_PCI_BRIDGE+0x14)     // PMM 1 Mask/Attributes
+#define PCIL0_PMM1PCILA      (_PPC405GP_PCI_BRIDGE+0x18)     // PMM 1 PCI Low Address
+#define PCIL0_PMM1PDIHA      (_PPC405GP_PCI_BRIDGE+0x1C)     // PMM 1 PCI High Address
+#define PCIL0_PMM2LA         (_PPC405GP_PCI_BRIDGE+0x20)     // PMM 2 Local address
+#define PCIL0_PMM2MA         (_PPC405GP_PCI_BRIDGE+0x24)     // PMM 2 Mask/Attributes
+#define PCIL0_PMM2PCILA      (_PPC405GP_PCI_BRIDGE+0x28)     // PMM 2 PCI Low Address
+#define PCIL0_PMM2PCIHA      (_PPC405GP_PCI_BRIDGE+0x2C)     // PMM 2 PCI High Address
+#define PCIL0_PTM1MS         (_PPC405GP_PCI_BRIDGE+0x30)     // PTM 1 Memory Size/Attribute
+#define PCIL0_PTM1LA         (_PPC405GP_PCI_BRIDGE+0x34)     // PTM 1 Local address
+#define PCIL0_PTM2MS         (_PPC405GP_PCI_BRIDGE+0x38)     // PTM 2 Memory Size/Attribute
+#define PCIL0_PTM2LA         (_PPC405GP_PCI_BRIDGE+0x3C)     // PTM 2 Local address
+
+// Access to local/bridge PCI configuration registers
+#define PCIC0_CFGADDR        (_PPC405GP_PCI_IO+0x00C00000)   // Indirect address pointer
+#define PCIC0_CFGDATA        (_PPC405GP_PCI_IO+0x00C00004)   // Indirect data
+
+// Debug control registers (SPR)
+#define SPR_DBCR0       0x3F2
+
+#endif // PPC4XX_405 || PPC4XX_405GP
 
 // Timer control (special) registers
 #define SPR_PIT    987
@@ -154,6 +321,27 @@
 
 #endif //  CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
 
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+//
+// Memory mapped peripherals
+//
+#define _PPC405GP_UART0            0xEF600300 
+#define _PPC405GP_UART1            0xEF600400 
+#define _PPC405GP_IIC0             0xEF600500 
+#define _PPC405GP_OPB_ARBITER      0xEF600600 
+#define _PPC405GP_GPIO             0xEF600700 
+#define _PPC405GP_ENET             0xEF600800 
+#define _PPC405GP_PCI_BRIDGE       0xEF400000
+#define _PPC405GP_PCI_IO           0xEE000000
+//
+// Window to PCI memory space (256MB, must be configured by target)
+#define _PPC405GP_PCI_MEM          0xA0000000
+//
+// On-chip memory (4K only, must be configured by target platform)
+//
+#define _PPC405GP_OCM              0xD0000000
+#endif // 405GP
+
 //-----------------------------------------------------------------------------
 #endif // ifdef CYGONCE_HAL_VAR_REGS_H
 // End of var_regs.h
--- a/packages/hal/powerpc/ppc40x/current/include/variant.inc
+++ b/packages/hal/powerpc/ppc40x/current/include/variant.inc
@@ -2,15 +2,16 @@
 #define CYGONCE_HAL_VARIANT_INC
 ##=============================================================================
 ##
-##	variant.inc
+##    variant.inc
 ##
-##	PPC40x family assembler header file
+##    PPC40x family assembler header file
 ##
 ##=============================================================================
 #####ECOSGPLCOPYRIGHTBEGIN####
 ## -------------------------------------------
 ## This file is part of eCos, the Embedded Configurable Operating System.
 ## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2002, 2003 Gary Thomas
 ##
 ## eCos is free software; you can redistribute it and/or modify it under
 ## the terms of the GNU General Public License as published by the Free
@@ -42,23 +43,23 @@
 ##=============================================================================
 #######DESCRIPTIONBEGIN####
 ##
-## Author(s): 	jskov
-## Contributors:jskov, gthomas
-## Date:	2000-08-27
-## Purpose:	MPCxxx family definitions.
-## Description:	This file contains various definitions and macros that are
-##              useful for writing assembly code for the PPC40x CPU family.
+## Author(s):     jskov
+## Contributors:  jskov, gthomas
+## Date:          2000-08-27
+## Purpose:       PPC40x family support
+## Description:   This file contains various definitions and macros that are
+##                useful for writing assembly code for the PPC40x CPU family.
 ## Usage:
-##		#include <cyg/hal/variant.inc>
-##		...
-##		
+##        #include <cyg/hal/variant.inc>
+##        ...
+##        
 ##
 ######DESCRIPTIONEND####
 ##
 ##=============================================================================
 
 #include <pkgconf/hal.h>
-	
+    
 #undef CYG_MSR_COMMON
 #define CYG_MSR_COMMON (MSR_ME | MSR_RI)
 
@@ -74,17 +75,17 @@
         .p2align 8
         .globl  __exception_\name
 __exception_\name:
-	# Variable timer interrupt
+    # Variable timer interrupt
         mtspr   SPRG1,r3                     # stash some work registers away
         mtspr   SPRG2,r4                    
         li      r4,0x1000                    # vector offset
-	b	0f
-	# Fixed timer interrupt
+        b       0f
+    # Fixed timer interrupt
         mtspr   SPRG1,r3                     # stash some work registers away
         mtspr   SPRG2,r4                    
         li      r4,0x1010                    # vector offset
-	b	0f
-	# Watchdog timer interrupt
+        b       0f
+    # Watchdog timer interrupt
         mtspr   SPRG1,r3                     # stash some work registers away
         mtspr   SPRG2,r4                    
         li      r4,0x1020                    # vector offset
@@ -93,29 +94,29 @@ 0:      mtspr   SPRG3,r5
         lwz     r3,0(r3)                     # address of vsr
         mflr    r5                           # save link register
         mtlr    r3                           # put vsr address into it
-	mr	r3,r4			     # original vector
+        mr      r3,r4                        # original vector
         mfcr    r4                           # stash CR
         blr                                  # go to common code
         .endm
 
         .macro hal_extra_vectors
-	timer_vector		ppc40x_timers
-	exception_vector	data_TLB_miss
-	exception_vector	instr_TLB_miss
-	exception_vector	reserved_01300
-	exception_vector	reserved_01400
-	exception_vector	reserved_01500
-	exception_vector	reserved_01600
-	exception_vector	reserved_01700
-	exception_vector	reserved_01800
-	exception_vector	reserved_01900
-	exception_vector	reserved_01A00
-	exception_vector	reserved_01B00
-	exception_vector	reserved_01C00
-	exception_vector	reserved_01D00
-	exception_vector	reserved_01E00
-	exception_vector	reserved_01F00
-	exception_vector	ppc40x_debug
+         timer_vector        ppc40x_timers   // 0x1000
+         exception_vector    data_TLB_miss   // 0x1100
+         exception_vector    instr_TLB_miss  // 0x1200
+         exception_vector    reserved_01300
+         exception_vector    reserved_01400
+         exception_vector    reserved_01500
+         exception_vector    reserved_01600
+         exception_vector    reserved_01700
+         exception_vector    reserved_01800
+         exception_vector    reserved_01900
+         exception_vector    reserved_01A00
+         exception_vector    reserved_01B00
+         exception_vector    reserved_01C00
+         exception_vector    reserved_01D00
+         exception_vector    reserved_01E00
+         exception_vector    reserved_01F00
+         exception_vector    ppc40x_debug
         .endm
 
 ##-----------------------------------------------------------------------------
@@ -124,11 +125,11 @@ 0:      mtspr   SPRG3,r5
 ## Initialize CPU to a post-reset state, ensuring the ground doesn''t
 ## shift under us while we try to set things up.
         
-        .macro hal_cpu_init
+         .macro hal_cpu_init
         # Set up MSR (disable MMU for now)
         lwi     r3,(CYG_MSR & ~(MSR_IR | MSR_DR))
         sync
-	mfmsr	r4
+        mfmsr   r4
         mtmsr   r3
         sync
         .endm
@@ -139,6 +140,7 @@ 0:      mtspr   SPRG3,r5
 #ifndef CYGPKG_HAL_PPC_MON_DEFINED
 
 #if     defined(CYG_HAL_STARTUP_ROM) ||                 \
+        defined(CYG_HAL_STARTUP_ROMRAM) || \
         (       defined(CYG_HAL_STARTUP_RAM) &&         \
                 !defined(CYGSEM_HAL_USE_ROM_MONITOR))
 
@@ -162,11 +164,11 @@ 1:
         cmplw   r3,r5                   # compare
         blt     1b                      # loop if not yet done
 2:
+#endif
 
-	# Ensure that the vectors will come from 0x0000
-	lwi	r4,0
-	mtspr	SPR_EVPR,r4
-#endif
+        # Ensure that the vectors will come from 0x0000
+        lwi     r4,0
+        mtspr   SPR_EVPR,r4
 
         # Next initialize the VSR table. This happens whether the
         # vectors were copied to RAM or not.
@@ -196,6 +198,11 @@ 1:      stwu    r3,4(r4)
         # the rest are left to the ROM for now...
 
         .macro  hal_mon_init
+
+        # Ensure that the vectors will come from 0x0000
+        lwi     r4,0
+        mtspr   SPR_EVPR,r4
+
         lwi     r3,cyg_hal_default_interrupt_vsr
         lwi     r4,hal_vsr_table
         stw     r3,CYGNUM_HAL_VECTOR_INTERRUPT*4(r4)
@@ -219,10 +226,10 @@ 1:      stwu    r3,4(r4)
 
 ##-----------------------------------------------------------------------------
 ## PPC40x exception state handling
-        .macro	hal_variant_save regs
+        .macro    hal_variant_save regs
         .endm
 
-        .macro	hal_variant_load regs
+        .macro    hal_variant_load regs
         .endm
 
 ##-----------------------------------------------------------------------------
@@ -235,31 +242,40 @@ 1:      stwu    r3,4(r4)
 
 ## Decode the EXISR appropriately
 
+#ifndef CYGPKG_HAL_POWERPC_INTC_DEFINED
 #define CYGPKG_HAL_POWERPC_INTC_DEFINED
         # decode the interrupt
-	# the interrupt vector will be 0x500 or 0x10x0
-	# 0x0500 = external, must be decoded via EXISR
-	# 0x10X0 = timer, X is the timer type
-	# r3 used as scratch
-	.macro  hal_intc_decode dreg,state
+        # the interrupt vector will be 0x500 or 0x10x0
+        # 0x0500 = external, must be decoded via hardware (e.g. EXISR)
+        # 0x10X0 = timer, X is the timer type
+        # r3 used as scratch
+        .macro  hal_intc_decode dreg,state
         lwz     \dreg,CYGARC_PPCREG_VECTOR(\state) # retrieve vector number,
-	extrwi.	\dreg,\dreg,1,19		# isolate bit 19
-	beq	0f				# timer interrupt = 1
+        extrwi. \dreg,\dreg,1,19        # isolate bit 19
+        beq     0f                      # timer interrupt = 1
         lwz     \dreg,CYGARC_PPCREG_VECTOR(\state) # retrieve vector number,
-	extrwi	\dreg,\dreg,2,26		# isolate bits 26-27
-	addi	\dreg,\dreg,CYGNUM_HAL_INTERRUPT_VAR_TIMER # FIXME
-	b	1f
-0:	mfdcr	r3,DCR_EXISR			# Interrupt status register
-	lwi	\dreg,0x8FF0001F		# significant bits
-	and	\dreg,\dreg,r3
-	cntlzw	r3,\dreg			# find highest "1" bit
-	slwi	r3,r3,2
-	lwi	\dreg,EXISR_TAB			# convert bit # to signal #
-	lwzx	\dreg,\dreg,r3
+        extrwi  \dreg,\dreg,2,26        # isolate bits 26-27
+        addi    \dreg,\dreg,CYGNUM_HAL_INTERRUPT_VAR_TIMER # FIXME
+        b       1f
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)
+0:      mfdcr   r3,DCR_EXISR            # Interrupt status register
+        lwi     \dreg,0x8FF0001F        # significant bits
+        and     \dreg,\dreg,r3
+        cntlzw  r3,\dreg                # find highest "1" bit
+        slwi    r3,r3,2
+        lwi     \dreg,EXISR_TAB         # convert bit # to signal #
+        lwzx    \dreg,\dreg,r3
+#elif defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+0:      mfdcr   r3,DCR_UIC0_MSR          # Status register
+        cntlzw  \dreg,r3                # find highest "1" bit
+        addi    \dreg,\dreg,2
+#else
+#error "No interrupt handling for variant"                
+#endif
 1:      stw     \dreg,CYGARC_PPCREG_VECTOR(\state) # update vector in state frame.
-        slwi    \dreg,\dreg,2                   # convert to byte offset.
+        slwi    \dreg,\dreg,2                      # convert to byte offset.
         .endm                              
-
+#endif
 
 #------------------------------------------------------------------------------
 #endif // ifndef CYGONCE_HAL_VARIANT_INC
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/ppc40x/current/src/hal_diag.c
@@ -0,0 +1,414 @@
+//=============================================================================
+//
+//      hal_diag.c
+//
+//      HAL diagnostic I/O code
+//
+//=============================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//=============================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):   hmt
+// Contributors:hmt, gthomas
+// Date:        1999-06-08
+// Purpose:     HAL diagnostic output
+// Description: Implementations of HAL diagnostic I/O support.
+//
+//####DESCRIPTIONEND####
+//
+//=============================================================================
+
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
+#include <pkgconf/hal.h>
+
+#include <cyg/infra/cyg_type.h>         // base types
+#include <cyg/infra/cyg_trac.h>         // tracing macros
+#include <cyg/infra/cyg_ass.h>          // assertion macros
+
+#include <cyg/hal/hal_io.h>             // IO macros
+#include <cyg/hal/hal_diag.h>
+#include <cyg/hal/hal_intr.h>           // Interrupt macros
+#include <cyg/hal/drv_api.h>
+
+#if defined(CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS)
+#include <cyg/hal/hal_stub.h>           // hal_output_gdb_string
+#endif
+
+#include <cyg/hal/ppc_regs.h>
+
+//=============================================================================
+// Serial driver
+//=============================================================================
+
+//-----------------------------------------------------------------------------
+// There are two serial ports.
+#define CYG_DEV_SERIAL_BASE_A    _PPC405GP_UART0
+#define CYG_DEV_SERIAL_BASE_B    _PPC405GP_UART1
+
+//-----------------------------------------------------------------------------
+// Define the serial registers. The PPC405GP has 16552 UART(s) builtin.
+//
+#define CYG_DEV_SERIAL_RBR   0x00  // receiver buffer register, read, dlab = 0
+#define CYG_DEV_SERIAL_THR   0x00 // transmitter holding register, write, dlab = 0
+#define CYG_DEV_SERIAL_DLL   0x00 // divisor latch (LS), read/write, dlab = 1
+#define CYG_DEV_SERIAL_IER   0x01 // interrupt enable register, read/write, dlab = 0
+#define CYG_DEV_SERIAL_DLM   0x01 // divisor latch (MS), read/write, dlab = 1
+#define CYG_DEV_SERIAL_IIR   0x02 // interrupt identification register, read, dlab = 0
+#define CYG_DEV_SERIAL_FCR   0x02 // fifo control register, write, dlab = 0
+#define CYG_DEV_SERIAL_AFR   0x02 // alternate function register, read/write, dlab = 1
+#define CYG_DEV_SERIAL_LCR   0x03 // line control register, read/write
+#define CYG_DEV_SERIAL_MCR   0x04
+#define CYG_DEV_SERIAL_MCR_A 0x04
+#define CYG_DEV_SERIAL_MCR_B 0x04
+#define CYG_DEV_SERIAL_LSR   0x05 // line status register, read
+#define CYG_DEV_SERIAL_MSR   0x06 // modem status register, read
+#define CYG_DEV_SERIAL_SCR   0x07 // scratch pad register
+
+// The interrupt enable register bits.
+#define SIO_IER_ERDAI   0x01            // enable received data available irq
+#define SIO_IER_ETHREI  0x02            // enable THR empty interrupt
+#define SIO_IER_ELSI    0x04            // enable receiver line status irq
+#define SIO_IER_EMSI    0x08            // enable modem status interrupt
+
+// The interrupt identification register bits.
+#define SIO_IIR_IP      0x01            // 0 if interrupt pending
+#define SIO_IIR_ID_MASK 0x0e            // mask for interrupt ID bits
+#define ISR_Tx  0x02
+#define ISR_Rx  0x04
+
+// The line status register bits.
+#define SIO_LSR_DR      0x01            // data ready
+#define SIO_LSR_OE      0x02            // overrun error
+#define SIO_LSR_PE      0x04            // parity error
+#define SIO_LSR_FE      0x08            // framing error
+#define SIO_LSR_BI      0x10            // break interrupt
+#define SIO_LSR_THRE    0x20            // transmitter holding register empty
+#define SIO_LSR_TEMT    0x40            // transmitter register empty
+#define SIO_LSR_ERR     0x80            // any error condition
+
+// The modem status register bits.
+#define SIO_MSR_DCTS  0x01              // delta clear to send
+#define SIO_MSR_DDSR  0x02              // delta data set ready
+#define SIO_MSR_TERI  0x04              // trailing edge ring indicator
+#define SIO_MSR_DDCD  0x08              // delta data carrier detect
+#define SIO_MSR_CTS   0x10              // clear to send
+#define SIO_MSR_DSR   0x20              // data set ready
+#define SIO_MSR_RI    0x40              // ring indicator
+#define SIO_MSR_DCD   0x80              // data carrier detect
+
+// The line control register bits.
+#define SIO_LCR_WLS0   0x01             // word length select bit 0
+#define SIO_LCR_WLS1   0x02             // word length select bit 1
+#define SIO_LCR_STB    0x04             // number of stop bits
+#define SIO_LCR_PEN    0x08             // parity enable
+#define SIO_LCR_EPS    0x10             // even parity select
+#define SIO_LCR_SP     0x20             // stick parity
+#define SIO_LCR_SB     0x40             // set break
+#define SIO_LCR_DLAB   0x80             // divisor latch access bit
+
+// The FIFO control register
+#define SIO_FCR_FCR0   0x01             // enable xmit and rcvr fifos
+#define SIO_FCR_FCR1   0x02             // clear RCVR FIFO
+#define SIO_FCR_FCR2   0x04             // clear XMIT FIFO
+
+
+//-----------------------------------------------------------------------------
+typedef struct {
+    cyg_uint8* base;
+    cyg_int32 msec_timeout;
+    int isr_vector;
+} channel_data_t;
+
+int
+cyg_var_baud_generator(int baud)
+{
+    int clock_rate, baud_clock, clock_divisor;
+    unsigned int cr0;
+
+    // Calculate baud rate clock divisor
+    CYGARC_MFDCR(DCR_CPC0_CR0, cr0);
+    clock_divisor = ((cr0 & 0x3E) >> 1) + 1;
+    clock_rate = ((CYGHWR_HAL_POWERPC_CPU_SPEED*1000000)/clock_divisor);
+    baud_clock = ((clock_rate)/16)/baud;
+    return baud_clock;
+}
+
+
+//-----------------------------------------------------------------------------
+static void
+init_serial_channel(const channel_data_t* __ch_data)
+{
+    cyg_uint8* base = __ch_data->base;
+    cyg_uint8 lcr;
+    int baud_clock = cyg_var_baud_generator(CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD);
+
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_IER, 0);
+
+    // Disable and clear FIFOs (need to enable to clear).
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_FCR,
+                    (SIO_FCR_FCR0 | SIO_FCR_FCR1 | SIO_FCR_FCR2));
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_FCR, 0);
+
+    // 8-1-no parity.
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_LCR, SIO_LCR_WLS0 | SIO_LCR_WLS1);
+
+    // Set speed to the default baud rate
+    HAL_READ_UINT8(base+CYG_DEV_SERIAL_LCR, lcr);
+    lcr |= SIO_LCR_DLAB;
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_LCR, lcr);
+
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_DLL, baud_clock & 0xFF);
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_DLM, (baud_clock >> 8) & 0xFF);
+    lcr &= ~SIO_LCR_DLAB;
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_LCR, lcr);
+
+    // Enable FIFOs (and clear them).
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_FCR,
+                    (SIO_FCR_FCR0 | SIO_FCR_FCR1 | SIO_FCR_FCR2));
+}
+
+static cyg_bool
+cyg_hal_var_serial_getc_nonblock(char* __ch_data, cyg_uint8* ch)
+{
+    cyg_uint8* base/* = ((channel_data_t*)__ch_data)->base*/;
+    cyg_uint8 lsr;
+
+    base = ((channel_data_t*)__ch_data)->base;
+
+    HAL_READ_UINT8(base+CYG_DEV_SERIAL_LSR, lsr);
+    if ((lsr & SIO_LSR_DR) == 0)
+        return false;
+
+    HAL_READ_UINT8(base+CYG_DEV_SERIAL_RBR, *ch);
+
+    return true;
+}
+
+
+cyg_uint8
+cyg_hal_var_serial_getc(void* __ch_data)
+{
+    cyg_uint8 ch;
+
+    while(!cyg_hal_var_serial_getc_nonblock(__ch_data, &ch));
+
+    return ch;
+}
+
+void
+cyg_hal_var_serial_putc(void* __ch_data, cyg_uint8 c)
+{
+    cyg_uint8* base = ((channel_data_t*)__ch_data)->base;
+    cyg_uint8 lsr;
+
+    do {
+        HAL_READ_UINT8(base+CYG_DEV_SERIAL_LSR, lsr);
+    } while ((lsr & SIO_LSR_THRE) == 0);
+
+    HAL_WRITE_UINT8(base+CYG_DEV_SERIAL_THR, c);
+
+    // Hang around until the character has been safely sent.
+    do {
+        HAL_READ_UINT8(base+CYG_DEV_SERIAL_LSR, lsr);
+    } while ((lsr & SIO_LSR_THRE) == 0);
+}
+
+static const channel_data_t channels[2] = {
+    { (cyg_uint8*)CYG_DEV_SERIAL_BASE_A, 1000, CYGNUM_HAL_INTERRUPT_UART0},
+#if (CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS > 1)
+    { (cyg_uint8*)CYG_DEV_SERIAL_BASE_B, 1000, CYGNUM_HAL_INTERRUPT_UART1},
+#endif
+};
+
+static void
+cyg_hal_var_serial_write(void* __ch_data, const cyg_uint8* __buf, 
+                         cyg_uint32 __len)
+{
+    while(__len-- > 0)
+        cyg_hal_var_serial_putc(__ch_data, *__buf++);
+}
+
+static void
+cyg_hal_var_serial_read(void* __ch_data, cyg_uint8* __buf, cyg_uint32 __len)
+{
+    while(__len-- > 0)
+        *__buf++ = cyg_hal_var_serial_getc(__ch_data);
+}
+
+cyg_bool
+cyg_hal_var_serial_getc_timeout(void* __ch_data, cyg_uint8* ch)
+{
+    int delay_count;
+    channel_data_t* chan = (channel_data_t*)__ch_data;
+    cyg_bool res;
+
+    delay_count = chan->msec_timeout * 10; // delay in .1 ms steps
+    for(;;) {
+        res = cyg_hal_var_serial_getc_nonblock(__ch_data, ch);
+        if (res || 0 == delay_count--)
+            break;
+        
+        CYGACC_CALL_IF_DELAY_US(100);
+    }
+    return res;
+}
+
+static int
+cyg_hal_var_serial_control(void *__ch_data, __comm_control_cmd_t __func, ...)
+{
+    static int irq_state = 0;
+    channel_data_t* chan = (channel_data_t*)__ch_data;
+    cyg_uint8 ier;
+    int ret = 0;
+
+    switch (__func) {
+    case __COMMCTL_IRQ_ENABLE:
+        HAL_INTERRUPT_UNMASK(chan->isr_vector);
+        HAL_INTERRUPT_SET_LEVEL(chan->isr_vector, 1);
+        HAL_READ_UINT8(chan->base+CYG_DEV_SERIAL_IER, ier);
+        ier |= SIO_IER_ERDAI;
+        HAL_WRITE_UINT8(chan->base+CYG_DEV_SERIAL_IER, ier);
+        irq_state = 1;
+        break;
+    case __COMMCTL_IRQ_DISABLE:
+        ret = irq_state;
+        irq_state = 0;
+        HAL_INTERRUPT_MASK(chan->isr_vector);
+        HAL_READ_UINT8(chan->base+CYG_DEV_SERIAL_IER, ier);
+        ier &= ~SIO_IER_ERDAI;
+        HAL_WRITE_UINT8(chan->base+CYG_DEV_SERIAL_IER, ier);
+        break;
+    case __COMMCTL_DBG_ISR_VECTOR:
+        ret = chan->isr_vector;
+        break;
+    case __COMMCTL_SET_TIMEOUT:
+    {
+        va_list ap;
+
+        va_start(ap, __func);
+
+        ret = chan->msec_timeout;
+        chan->msec_timeout = va_arg(ap, cyg_uint32);
+
+        va_end(ap);
+    }        
+    default:
+        break;
+    }
+    return ret;
+}
+
+static int
+cyg_hal_var_serial_isr(void *__ch_data, int* __ctrlc, 
+                       CYG_ADDRWORD __vector, CYG_ADDRWORD __data)
+{
+    channel_data_t* chan = (channel_data_t*)__ch_data;
+    cyg_uint8 _iir;
+    int res = 0;
+
+    HAL_READ_UINT8(chan->base+CYG_DEV_SERIAL_IIR, _iir);
+    _iir &= SIO_IIR_ID_MASK;
+
+    *__ctrlc = 0;
+    if ( ISR_Rx == _iir ) {
+        cyg_uint8 c, lsr;
+        HAL_READ_UINT8(chan->base+CYG_DEV_SERIAL_LSR, lsr);
+        if (lsr & SIO_LSR_DR) {
+
+            HAL_READ_UINT8(chan->base+CYG_DEV_SERIAL_RBR, c);
+
+            if( cyg_hal_is_break( &c , 1 ) )
+                *__ctrlc = 1;
+        }
+
+        // Acknowledge the interrupt
+        HAL_INTERRUPT_ACKNOWLEDGE(chan->isr_vector);
+        res = CYG_ISR_HANDLED;
+    }
+    return res;
+}
+
+void
+cyg_hal_var_serial_init(void)
+{
+    hal_virtual_comm_table_t* comm;
+    int cur = CYGACC_CALL_IF_SET_CONSOLE_COMM(CYGNUM_CALL_IF_SET_COMM_ID_QUERY_CURRENT);
+
+    // Disable interrupts.
+    HAL_INTERRUPT_MASK(channels[0].isr_vector);
+#if (CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS > 1)
+    HAL_INTERRUPT_MASK(channels[1].isr_vector);
+#endif
+
+    // Init channels
+    init_serial_channel(&channels[0]);
+#if (CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS > 1)
+    init_serial_channel(&channels[1]);
+#endif
+
+    // Setup procs in the vector table
+
+    // Set channel 0
+    CYGACC_CALL_IF_SET_CONSOLE_COMM(0);
+    comm = CYGACC_CALL_IF_CONSOLE_PROCS();
+    CYGACC_COMM_IF_CH_DATA_SET(*comm, &channels[0]);
+    CYGACC_COMM_IF_WRITE_SET(*comm, cyg_hal_var_serial_write);
+    CYGACC_COMM_IF_READ_SET(*comm, cyg_hal_var_serial_read);
+    CYGACC_COMM_IF_PUTC_SET(*comm, cyg_hal_var_serial_putc);
+    CYGACC_COMM_IF_GETC_SET(*comm, cyg_hal_var_serial_getc);
+    CYGACC_COMM_IF_CONTROL_SET(*comm, cyg_hal_var_serial_control);
+    CYGACC_COMM_IF_DBG_ISR_SET(*comm, cyg_hal_var_serial_isr);
+    CYGACC_COMM_IF_GETC_TIMEOUT_SET(*comm, cyg_hal_var_serial_getc_timeout);
+
+#if (CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS > 1)
+    // Set channel 1
+    CYGACC_CALL_IF_SET_CONSOLE_COMM(1);
+    comm = CYGACC_CALL_IF_CONSOLE_PROCS();
+    CYGACC_COMM_IF_CH_DATA_SET(*comm, &channels[1]);
+    CYGACC_COMM_IF_WRITE_SET(*comm, cyg_hal_var_serial_write);
+    CYGACC_COMM_IF_READ_SET(*comm, cyg_hal_var_serial_read);
+    CYGACC_COMM_IF_PUTC_SET(*comm, cyg_hal_var_serial_putc);
+    CYGACC_COMM_IF_GETC_SET(*comm, cyg_hal_var_serial_getc);
+    CYGACC_COMM_IF_CONTROL_SET(*comm, cyg_hal_var_serial_control);
+    CYGACC_COMM_IF_DBG_ISR_SET(*comm, cyg_hal_var_serial_isr);
+    CYGACC_COMM_IF_GETC_TIMEOUT_SET(*comm, cyg_hal_var_serial_getc_timeout);
+#endif
+    
+    // Restore original console
+    CYGACC_CALL_IF_SET_CONSOLE_COMM(cur);
+}
+
+// EOF hal_diag.c
new file mode 100644
--- /dev/null
+++ b/packages/hal/powerpc/ppc40x/current/src/ppc405_pci.c
@@ -0,0 +1,315 @@
+//==========================================================================
+//
+//      ppc405_pci.c
+//
+//      HAL variant support code for PCI on PowerPC 405GP
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    Gary Thomas <gary@mlbassoc.com>
+// Contributors: 
+// Date:         2003-09-02
+// Purpose:      HAL PCI support
+// Description:  Implementations of HAL PCI interfaces
+//
+//####DESCRIPTIONEND####
+//
+//========================================================================*/
+
+#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
+#include <pkgconf/hal.h>
+#include <pkgconf/system.h>
+#include CYGBLD_HAL_PLATFORM_H
+
+#include <cyg/infra/cyg_type.h>         // base types
+#include <cyg/infra/cyg_trac.h>         // tracing macros
+#include <cyg/infra/cyg_ass.h>          // assertion macros
+#include <cyg/infra/diag.h>             // diag_printf() and friends
+
+#include <cyg/hal/hal_io.h>             // IO macros
+#include <cyg/hal/hal_arch.h>           // Register state info
+#include <cyg/hal/hal_diag.h>
+#include <cyg/hal/hal_intr.h>           // Interrupt names
+#include <cyg/hal/hal_cache.h>
+#include <cyg/hal/ppc_regs.h>           // Hardware definitions
+#include <cyg/hal/hal_if.h>             // calling interface API
+
+#include <pkgconf/io_pci.h>
+#include <cyg/io/pci_hw.h>
+#include <cyg/io/pci.h>
+
+// PCI support
+
+externC void
+hal_ppc405_pci_init(void)
+{
+    static int _init = 0;
+    cyg_uint8 next_bus;
+    cyg_uint32 cmd_state, bridge_state;
+
+    if (_init) return;
+    _init = 1;
+
+    // Configure PCI bridge
+    HAL_WRITE_UINT32LE(PCIL0_PMM0PCILA, 0);
+    HAL_WRITE_UINT32LE(PCIL0_PMM0PCIHA, 0);
+    HAL_WRITE_UINT32LE(PCIL0_PMM0LA, HAL_PCI_PHYSICAL_MEMORY_BASE);
+    HAL_WRITE_UINT32LE(PCIL0_PMM0MA, ~(0x10000000-1) | 0x00000001);
+    HAL_PCI_CFG_WRITE_UINT32(0, CYG_PCI_DEV_MAKE_DEVFN(0,0), CYG_PCI_CFG_BAR_1, 0);    
+    HAL_WRITE_UINT32LE(PCIL0_PTM1LA, 0);
+    HAL_WRITE_UINT32LE(PCIL0_PTM1MS, ~(0x10000000-1) | 0x00000001);
+    // Indicate that the bridge has been configured
+    HAL_PCI_CFG_READ_UINT32(0, CYG_PCI_DEV_MAKE_DEVFN(0,0), 0x60, bridge_state);
+    bridge_state |= 0x0001;
+    HAL_PCI_CFG_WRITE_UINT32(0, CYG_PCI_DEV_MAKE_DEVFN(0,0), 0x60, bridge_state);
+    // Setup for bus mastering
+    HAL_PCI_CFG_READ_UINT32(0, CYG_PCI_DEV_MAKE_DEVFN(0,0),
+                            CYG_PCI_CFG_COMMAND, cmd_state);
+    if ((cmd_state & CYG_PCI_CFG_COMMAND_MEMORY) == 0) {
+        diag_printf("Configure PCI bus\n");
+        HAL_PCI_CFG_WRITE_UINT32(0, CYG_PCI_DEV_MAKE_DEVFN(0,0),
+                                 CYG_PCI_CFG_COMMAND,
+                                 CYG_PCI_CFG_COMMAND_MEMORY |
+                                 CYG_PCI_CFG_COMMAND_MASTER |
+                                 CYG_PCI_CFG_COMMAND_PARITY |
+                                 CYG_PCI_CFG_COMMAND_SERR);
+
+        // Setup latency timer field
+        HAL_PCI_CFG_WRITE_UINT8(0, CYG_PCI_DEV_MAKE_DEVFN(0,0),
+                                CYG_PCI_CFG_LATENCY_TIMER, 32);
+
+        // Configure PCI bus.
+        next_bus = 1;
+        cyg_pci_configure_bus(0, &next_bus);
+    }
+    if (1){
+        cyg_uint8 req;                                                            
+        cyg_uint8 devfn;
+        cyg_pci_device_id devid;
+        cyg_pci_device dev_info;
+        int i;
+
+        devid = CYG_PCI_DEV_MAKE_ID(next_bus-1, 0) | CYG_PCI_NULL_DEVFN;
+        while (cyg_pci_find_next(devid, &devid)) {
+            devfn = CYG_PCI_DEV_GET_DEVFN(devid);
+            cyg_pci_get_device_info(devid, &dev_info);
+            HAL_PCI_CFG_READ_UINT8(0, devfn, CYG_PCI_CFG_INT_PIN, req);         
+
+            diag_printf("\n");
+            diag_printf("Bus: %d", CYG_PCI_DEV_GET_BUS(devid));
+            diag_printf(", PCI Device: %d", CYG_PCI_DEV_GET_DEV(devfn));
+            diag_printf(", PCI Func: %d\n", CYG_PCI_DEV_GET_FN(devfn));
+            diag_printf("  Vendor Id: 0x%04X", dev_info.vendor);
+            diag_printf(", Device Id: 0x%04X", dev_info.device);
+            diag_printf(", Command: 0x%04X", dev_info.command);
+            diag_printf(", IRQ: %d\n", req);
+            for (i = 0; i < dev_info.num_bars; i++) {
+                diag_printf("  BAR[%d]    0x%08x /", i, dev_info.base_address[i]);
+                diag_printf(" probed size 0x%08x / CPU addr 0x%08x\n",
+                            dev_info.base_size[i], dev_info.base_map[i]);
+            }
+        }
+    }
+}
+
+externC void 
+hal_ppc405_pci_translate_interrupt(int bus, int devfn, int *vec, int *valid)
+{
+    cyg_uint8 req;                                                            
+    cyg_uint8 dev = CYG_PCI_DEV_GET_DEV(devfn);
+
+    if ((dev >= CYG_PCI_MIN_DEV) && (dev < CYG_PCI_MAX_DEV)) {
+        HAL_PCI_CFG_READ_UINT8(bus, devfn, CYG_PCI_CFG_INT_PIN, req);         
+        if (0 != req) {                                                           
+//
+// This mapping comes from this table, based on how the backplane is wired
+// IRQ assignments (Acrosser):    
+
+//               CPU        Slot1      Slot2    Slot3    Slot4
+
+// IRQ1     PCI INTD        INTB       INTA     INTD      na
+// IRQ2     PCI INTC        INTA       INTD     INTC      na
+// IRQ3     PCI INTB        INTD       INTC     INTB      na
+// IRQ4     PCI INTA        INTC       INTB     INTA      na
+#define _IRQ1 CYGNUM_HAL_INTERRUPT_IRQ1
+#define _IRQ2 CYGNUM_HAL_INTERRUPT_IRQ2
+#define _IRQ3 CYGNUM_HAL_INTERRUPT_IRQ3
+#define _IRQ4 CYGNUM_HAL_INTERRUPT_IRQ4
+            char pci_irq_table[][4] =
+                /*
+                 *      PCI IDSEL/INTPIN->INTLINE
+                 *      A       B       C       D
+                 */
+                {
+                    {_IRQ3, _IRQ3, _IRQ3, _IRQ3},	/* IDSEL 1 - 2nd LAN */
+                    {_IRQ3, _IRQ3, _IRQ3, _IRQ3},	/* IDSEL 2 - USB */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 3 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 4 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 5 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 6 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 7 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 8 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 9 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 10 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 11 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 12 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 13 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 14 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 15 - unavailable */
+                    {   -1,    -1,    -1,    -1},	/* IDSEL 16 - unavailable */
+                    {_IRQ1, _IRQ4, _IRQ3, _IRQ2},	/* IDSEL 17 - PCI slot 2 */
+                    {_IRQ4, _IRQ3, _IRQ2, _IRQ1},	/* IDSEL 18 - PCI slot 3 */
+                    {_IRQ1, _IRQ4, _IRQ3, _IRQ2},	/* IDSEL 19 - PCI slot 2 */
+                    {_IRQ2, _IRQ1, _IRQ4, _IRQ3},	/* IDSEL 20 - PCI slot 1 */
+                };
+            *vec = pci_irq_table[dev-1][req-1];
+            *valid = (*vec != -1);
+        } else {                                                                    
+            /* Device will not generate interrupt requests. */                      
+            *valid = false;                                                        
+        }                                                                           
+        diag_printf("Int - dev: %d, req: %d, vector: %d\n", dev, req, *vec);
+    } else {
+        *valid = false;  // Invalid device
+    }
+}
+
+// PCI configuration space access
+#define _EXT_ENABLE 0x80000000  // Could be 0x80000000
+
+static __inline__ cyg_uint32
+_cfg_addr(int bus, int devfn, int offset)
+{
+    return _EXT_ENABLE | (bus << 16) | (devfn << 8) | (offset << 0);
+}
+
+externC cyg_uint8 
+hal_ppc405_pci_cfg_read_uint8(int bus, int devfn, int offset)
+{
+    cyg_uint32 cfg_addr;
+    cyg_uint8 cfg_val = (cyg_uint8) 0xFF;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x) = ", __FUNCTION__, bus, devfn, offset);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_READ_UINT8LE(PCIC0_CFGDATA|(offset & 0x03), cfg_val);
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%x\n", cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    return cfg_val;
+}
+
+externC cyg_uint16 
+hal_ppc405_pci_cfg_read_uint16(int bus, int devfn, int offset)
+{
+    cyg_uint32 cfg_addr;
+    cyg_uint16 cfg_val = (cyg_uint16) 0xFFFF;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x) = ", __FUNCTION__, bus, devfn, offset);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_READ_UINT16LE(PCIC0_CFGDATA|(offset & 0x03), cfg_val);
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%x\n", cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    return cfg_val;
+}
+
+externC cyg_uint32 
+hal_ppc405_pci_cfg_read_uint32(int bus, int devfn, int offset)
+{
+    cyg_uint32 cfg_addr;
+    cyg_uint32 cfg_val = (cyg_uint32) 0xFFFFFFFF;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x) = ", __FUNCTION__, bus, devfn, offset);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_READ_UINT32LE(PCIC0_CFGDATA, cfg_val);
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%x\n", cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    return cfg_val;
+}
+
+externC void
+hal_ppc405_pci_cfg_write_uint8(int bus, int devfn, int offset, cyg_uint8 cfg_val)
+{
+    cyg_uint32 cfg_addr;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x, val=%x)\n", __FUNCTION__, bus, devfn, offset, cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_WRITE_UINT8LE(PCIC0_CFGDATA|(offset & 0x03), cfg_val);
+}
+
+externC void
+hal_ppc405_pci_cfg_write_uint16(int bus, int devfn, int offset, cyg_uint16 cfg_val)
+{
+    cyg_uint32 cfg_addr;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x, val=%x)\n", __FUNCTION__, bus, devfn, offset, cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_WRITE_UINT16LE(PCIC0_CFGDATA|(offset & 0x03), cfg_val);
+}
+
+externC void
+hal_ppc405_pci_cfg_write_uint32(int bus, int devfn, int offset, cyg_uint32 cfg_val)
+{
+    cyg_uint32 cfg_addr;
+
+#ifdef CYGPKG_IO_PCI_DEBUG
+    diag_printf("%s(bus=%x, devfn=%x, offset=%x, val=%x)\n", __FUNCTION__, bus, devfn, offset, cfg_val);
+#endif // CYGPKG_IO_PCI_DEBUG
+    cfg_addr = _cfg_addr(bus, devfn, offset);
+    HAL_WRITE_UINT32LE(PCIC0_CFGADDR, cfg_addr);
+    HAL_WRITE_UINT32LE(PCIC0_CFGDATA, cfg_val);
+}
+
+/*------------------------------------------------------------------------*/
+// EOF ppc405_pci.c
--- a/packages/hal/powerpc/ppc40x/current/src/var_intr.c
+++ b/packages/hal/powerpc/ppc40x/current/src/var_intr.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -59,6 +60,14 @@
 
 extern void hal_platform_IRQ_init(void);
 
+//
+// Sadly, the IBM PPC40x family of devices are only related by number
+// and not always by functionality.  In particular, the 403 has a
+// completely different interrupt controller than the 405.  For now
+// at least, these differences are controlled by CDL within this file.
+//
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)
 
 static cyg_uint32 exier_mask[] = {
     0x00000000, // Unused
@@ -295,6 +304,186 @@ externC void
 hal_ppc40x_interrupt_set_level(int vector, int level)
 {
 }
+#endif // CYGHWR_HAL_POWERPC_PPC4XX_403
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+
+cyg_uint32 _hold_tcr = 0;  // Shadow of hardware register
+
+externC void
+hal_variant_IRQ_init(void)
+{
+#ifndef HAL_PLF_INTERRUPT_INIT
+    // Ensure all interrupts masked (disabled) & cleared
+    CYGARC_MTDCR(DCR_UIC0_ER, 0);
+    CYGARC_MTDCR(DCR_UIC0_CR, 0);
+    CYGARC_MTDCR(DCR_UIC0_PR, 0xFFFFE000);
+    CYGARC_MTDCR(DCR_UIC0_TR, 0);
+    CYGARC_MTDCR(DCR_UIC0_VCR, 0);  // Makes vector identification easy
+    CYGARC_MTDCR(DCR_UIC0_SR, 0xFFFFFFFF);
+#else
+    HAL_PLF_INTERRUPT_INIT();
+#endif
+
+    // Disable timers
+    CYGARC_MTSPR(SPR_TCR, 0);
+
+    // Let the platform do any overrides
+    hal_platform_IRQ_init();
+}
+
+externC void 
+hal_ppc40x_interrupt_mask(int vector)
+{
+    cyg_uint32 exier, tcr;
+
+    switch (vector) {
+    case CYGNUM_HAL_INTERRUPT_first...CYGNUM_HAL_INTERRUPT_last:
+#ifndef HAL_PLF_INTERRUPT_MASK
+        CYGARC_MFDCR(DCR_UIC0_ER, exier);
+        exier &= ~(1<<(31-(vector-CYGNUM_HAL_INTERRUPT_405_BASE)));
+        CYGARC_MTDCR(DCR_UIC0_ER, exier);
+#else
+        HAL_PLF_INTERRUPT_MASK(vector);
+#endif
+        break;
+    case CYGNUM_HAL_INTERRUPT_VAR_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr &= ~TCR_PIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    case CYGNUM_HAL_INTERRUPT_FIXED_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr &= ~TCR_FIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    case CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr &= ~TCR_WIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    default:
+    }
+}
+
+externC void 
+hal_ppc40x_interrupt_unmask(int vector)
+{
+    cyg_uint32 exier, tcr;
+
+    switch (vector) {
+    case CYGNUM_HAL_INTERRUPT_first...CYGNUM_HAL_INTERRUPT_last:
+#ifndef HAL_PLF_INTERRUPT_UNMASK
+        CYGARC_MFDCR(DCR_UIC0_ER, exier);
+        exier |= (1<<(31-(vector-CYGNUM_HAL_INTERRUPT_405_BASE)));
+        CYGARC_MTDCR(DCR_UIC0_ER, exier);
+#else
+        HAL_PLF_INTERRUPT_UNMASK(vector);
+#endif
+        break;
+    case CYGNUM_HAL_INTERRUPT_VAR_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr |= TCR_PIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    case CYGNUM_HAL_INTERRUPT_FIXED_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr |= TCR_FIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    case CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER:
+        CYGARC_MFSPR(SPR_TCR, tcr);
+        tcr = _hold_tcr;
+        tcr |= TCR_WIE;
+        CYGARC_MTSPR(SPR_TCR, tcr);
+        _hold_tcr = tcr;
+        break;
+    default:
+    }
+}
+
+externC void 
+hal_ppc40x_interrupt_acknowledge(int vector)
+{
+    switch (vector) {
+    case CYGNUM_HAL_INTERRUPT_first...CYGNUM_HAL_INTERRUPT_last:
+#ifndef HAL_PLF_INTERRUPT_ACKNOWLEDGE
+        CYGARC_MTDCR(DCR_UIC0_SR, (1<<(31-(vector-CYGNUM_HAL_INTERRUPT_405_BASE))));
+#else
+        HAL_PLF_INTERRUPT_ACKNOWLEDGE(vector);
+#endif
+        break;
+    case CYGNUM_HAL_INTERRUPT_VAR_TIMER:
+        CYGARC_MTSPR(SPR_TSR, TSR_PIS);  // clear & acknowledge interrupt
+        break;
+    case CYGNUM_HAL_INTERRUPT_FIXED_TIMER:
+        CYGARC_MTSPR(SPR_TSR, TSR_FIS);  // clear & acknowledge interrupt
+        break;
+    case CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER:
+        CYGARC_MTSPR(SPR_TSR, TSR_WIS);  // clear & acknowledge interrupt
+        break;
+    default:
+    }
+}
+
+// Note: These functions are only [well] defined for "external" interrupts
+externC void 
+hal_ppc40x_interrupt_configure(int vector, int level, int dir)
+{
+#ifndef HAL_PLF_INTERRUPT_CONFIGURE
+    cyg_uint32 mask, new_state, iocr;
+
+    if ((vector >= CYGNUM_HAL_INTERRUPT_IRQ0) &&
+        (vector <= CYGNUM_HAL_INTERRUPT_IRQ6)) {
+        mask = (1<<(31-(vector-CYGNUM_HAL_INTERRUPT_405_BASE)));
+        // Set polarity
+        if (dir) {
+            // High true
+            new_state = mask;
+        } else {
+            // Low true
+            new_state = 0;
+        }
+        CYGARC_MFDCR(DCR_UIC0_PR, iocr);
+        iocr = (iocr & ~mask) | new_state;
+        CYGARC_MTDCR(DCR_UIC0_PR, iocr);
+        // Set edge/level
+        if (level == 0) {
+            // Edge triggered
+            new_state = mask;
+        } else {
+            // Level triggered
+            new_state = 0;
+        }
+        CYGARC_MFDCR(DCR_UIC0_TR, iocr);
+        iocr = (iocr & ~mask) | new_state;
+        CYGARC_MTDCR(DCR_UIC0_TR, iocr);
+    }
+#else
+    HAL_PLF_INTERRUPT_CONFIGURE(vector, level, dir);
+#endif
+}
+
+externC void 
+hal_ppc40x_interrupt_set_level(int vector, int level)
+{
+#ifndef HAL_PLF_INTERRUPT_SET_LEVEL
+    // Nothing to do for UIC
+#else
+    HAL_PLF_INTERRUPT_SET_LEVEL(vector, level);
+#endif
+}
+#endif // CYGHWR_HAL_POWERPC_PPC4XX_405
 
 // -------------------------------------------------------------------------
 // EOF var_intr.c
--- a/packages/hal/powerpc/ppc40x/current/src/var_misc.c
+++ b/packages/hal/powerpc/ppc40x/current/src/var_misc.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -56,16 +57,35 @@
 #define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
 #include <cyg/hal/ppc_regs.h>
 #include <cyg/infra/cyg_type.h>
-
+#include <cyg/hal/hal_io.h>             // I/O macros
+#include <cyg/hal/hal_if.h>             // Support (virtual vector)
 #include <cyg/hal/hal_mem.h>
+#include <cyg/infra/diag.h>
 
-void hal_ppc40x_clock_initialize(cyg_uint32 period);
+#ifdef CYGPKG_IO_PCI
+externC void hal_ppc405_pci_init(void);
+#endif
+
+externC void hal_ppc40x_clock_initialize(cyg_uint32 period);
+static  void hal_ppc405_i2c_init(void);
 
 //--------------------------------------------------------------------------
 void hal_variant_init(void)
 {
+    // Initialize I/O interfaces
+    hal_if_init();
+
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+    // Initialize I2C controller
+    hal_ppc405_i2c_init();
+#endif
+
     // Initialize real-time clock (for delays, etc, even if kernel doesn't use it)
     hal_ppc40x_clock_initialize(CYGNUM_HAL_RTC_PERIOD);
+
+#ifdef CYGPKG_IO_PCI
+    hal_ppc405_pci_init();
+#endif
 }
 
 
@@ -96,26 +116,38 @@ cyg_hal_map_memory (int id, CYG_ADDRESS 
     // There are 64 TLBs.
     max_tlbs = 64;
 
-    // Use the smallest "size" value which is big enough (round up)
-    for (sv = 0, lv = 0x400;  sv < 8;  sv++, lv <<= 2) {
-        if (lv >= size) break;        
-    }
+    // May need to use more than one slot since the TLB can only
+    // map 16MB max.
 
-    // Note: the process ID comes from the PID register (always 0)
-    epn = (virt & M_EPN_EPNMASK) | M_EPN_EV | M_EPN_SIZE(sv);
-    rpn = (phys & M_RPN_RPNMASK) | M_RPN_EX | M_RPN_WR;
+    while (size > 0) {
+        // Use the smallest "size" value which is big enough (round up)
+        for (sv = 0, lv = 0x400;  sv < 7;  sv++, lv <<= 2) {
+            if (lv >= size) break;        
+        }
+
+        // Note: the process ID comes from the PID register (always 0)
+        epn = (virt & M_EPN_EPNMASK) | M_EPN_EV | M_EPN_SIZE(sv);
+        rpn = (phys & M_RPN_RPNMASK) | M_RPN_EX | M_RPN_WR;
 
-    if (flags & CYGARC_MEMDESC_CI) {
-        rpn |= M_RPN_I;
-    }
+        if (flags & CYGARC_MEMDESC_CI) {
+            rpn |= M_RPN_I;
+        }
+#ifdef CYGSEM_HAL_DCACHE_STARTUP_MODE_WRITETHRU
+        // Only for cache-enabled regions
+        else {
+            rpn |= M_RPN_W;
+        }
+#endif
 
-    if (flags & CYGARC_MEMDESC_GUARDED) 
-        rpn |= M_RPN_G;
+        if (flags & CYGARC_MEMDESC_GUARDED) 
+            rpn |= M_RPN_G;
 
-    CYGARC_TLBWE(id, epn, rpn);
-    id++;
-
-    // Make caches default disabled when MMU is disabled.
+        CYGARC_TLBWE(id, epn, rpn);
+        id++;
+        size -= lv;
+        virt += lv;
+        phys += lv;
+    }
 
     return id;
 }
@@ -193,23 +225,137 @@ hal_ppc40x_delay_us(int us)
     cyg_uint32 pit_val1, pit_val2;
 
     delay_period = (_period * us) / 10000;
+    delay_period = ((_period / 10000) * us);
     delay = 0;
     CYGARC_MFSPR(SPR_PIT, pit_val1);
     while (delay < delay_period) {
         // Wait for clock to "tick"
         while (true) {
             CYGARC_MFSPR(SPR_PIT, pit_val2);
-            if (pit_val2 != pit_val1) break;
+            if (pit_val1 != pit_val2) break;
         }
-        if (pit_val2 > pit_val1) {
-            diff = pit_val2 - pit_val1;
+        // The counter ticks down
+        if (pit_val2 < pit_val1) {
+            diff = pit_val1 - pit_val2;
         } else {
-            diff = (pit_val2 + _period) - pit_val1;
+            diff = (_period - pit_val2) + pit_val1;
         }
         delay += diff;        
         pit_val1 = pit_val2;
     }
 }
 
+#if defined(CYGHWR_HAL_POWERPC_PPC4XX_405) || defined(CYGHWR_HAL_POWERPC_PPC4XX_405GP)
+//----------------------------------------------------------------------
+// I2C Support
+static void
+hal_ppc405_i2c_init(void)
+{
+    HAL_WRITE_UINT8(IIC0_CLKDIV, 6);  // 66MHz
+    HAL_WRITE_UINT8(IIC0_STS, (IIC0_STS_SCMP|IIC0_STS_IRQA));
+    HAL_WRITE_UINT8(IIC0_LMADR, 0);  // Clear interface
+    HAL_WRITE_UINT8(IIC0_HMADR, 0);
+    HAL_WRITE_UINT8(IIC0_LSADR, 0);
+    HAL_WRITE_UINT8(IIC0_HSADR, 0);
+    HAL_WRITE_UINT8(IIC0_EXTSTS, (IIC0_EXTSTS_IRQP|IIC0_EXTSTS_IRQD));
+    HAL_WRITE_UINT8(IIC0_MDCNTL, (IIC0_MDCNTL_FSDB|IIC0_MDCNTL_FMDB|IIC0_MDCNTL_EUBS));
+}
+
+externC bool
+hal_ppc405_i2c_put_bytes(int addr, cyg_uint8 *val, int len)
+{
+    cyg_uint8 stat, extstat, xfrcnt, cmd, size;
+    int i, j;
+
+    // The hardware can only move up to 4 bytes in a single operation
+    // This code breaks the request down into chunks of up to 4 bytes
+    // and checks the status after each chunk.
+    // Note: the actual device may impose additional size restrictions,
+    // e.g. some EEPROM devices may limit a single write to 32 bytes.
+    for (i = 0;  i < len;  i += size) {
+        HAL_WRITE_UINT8(IIC0_STS, (IIC0_STS_SCMP|IIC0_STS_IRQA));
+        HAL_WRITE_UINT8(IIC0_EXTSTS, (IIC0_EXTSTS_IRQP|IIC0_EXTSTS_IRQD));
+        HAL_WRITE_UINT8(IIC0_MDCNTL, (IIC0_MDCNTL_FSDB|IIC0_MDCNTL_FMDB));
+        cmd = IIC0_CNTL_RW_WRITE|IIC0_CNTL_PT;
+        size = (len - i);
+        if (size > 4) {
+            size = 4;
+            cmd |= IIC0_CNTL_CHT;
+        }
+        cmd |= ((size-1)<<IIC0_CNTL_TCT_SHIFT);
+        for (j = 0;  j < size;  j++) {
+            HAL_WRITE_UINT8(IIC0_MDBUF, val[i+j]);
+        }
+        HAL_WRITE_UINT8(IIC0_LMADR, addr);
+        HAL_WRITE_UINT8(IIC0_CNTL, cmd);
+        while (true) {
+            CYGACC_CALL_IF_DELAY_US(10);   // 10us
+            HAL_READ_UINT8(IIC0_STS, stat);
+            if ((stat & IIC0_STS_PT) == 0) {
+                if ((stat & IIC0_STS_ERR) != 0) {
+                    // Some sort of error
+                    HAL_READ_UINT8(IIC0_EXTSTS, extstat);                
+                    HAL_READ_UINT8(IIC0_XFRCNT, xfrcnt);                
+                    HAL_WRITE_UINT8(IIC0_EXTSTS, extstat);                
+                    HAL_WRITE_UINT8(IIC0_MDCNTL, (IIC0_MDCNTL_FSDB|IIC0_MDCNTL_FMDB));
+                    HAL_WRITE_UINT8(IIC0_STS, (IIC0_STS_SCMP|IIC0_STS_IRQA));
+                    diag_printf("%s addr: %x, len: %d, err: %x/%x, count: %d, cmd: %x\n", 
+                                __FUNCTION__, addr, len, stat, extstat, xfrcnt, cmd);
+                    diag_printf("buf: ");
+                    for (j = 0;  j < size;  j++) {
+                        diag_printf("0x%02x ", val[i+j]);
+                    }
+                    diag_printf("\n");
+                    return false;
+                }
+                break;
+            }
+        }
+    }
+    return true;
+}
+
+externC bool
+hal_ppc405_i2c_get_bytes(int addr, cyg_uint8 *val, int len)
+{
+    cyg_uint8 stat, extstat, _val, cmd;
+    int i, j, size;
+
+    for (i = 0;  i < len;  i += size) {
+        cmd = IIC0_CNTL_RW_READ|IIC0_CNTL_PT;
+        size = (len - i);
+        if (size > 4) {
+            size = 4;
+            cmd |= IIC0_CNTL_CHT;
+        }
+        cmd |= ((size-1)<<IIC0_CNTL_TCT_SHIFT);
+        HAL_WRITE_UINT8(IIC0_LMADR, addr);
+        HAL_WRITE_UINT8(IIC0_CNTL, cmd);
+        while (true) {
+            CYGACC_CALL_IF_DELAY_US(10);   // 10us
+            HAL_READ_UINT8(IIC0_STS, stat);
+            if ((stat & IIC0_STS_PT) == 0) {
+                if ((stat & IIC0_STS_ERR) != 0) {
+                    // Some sort of error
+                    HAL_READ_UINT8(IIC0_EXTSTS, extstat);                
+                    HAL_WRITE_UINT8(IIC0_EXTSTS, extstat);                
+                    HAL_WRITE_UINT8(IIC0_MDCNTL, (IIC0_MDCNTL_FSDB|IIC0_MDCNTL_FMDB));
+                    HAL_WRITE_UINT8(IIC0_STS, (IIC0_STS_SCMP|IIC0_STS_IRQA));
+                    diag_printf("%s addr: %x, len: %d, err: %x/%x\n", 
+                                __FUNCTION__, addr, len, stat, extstat);
+                    return false;
+                }
+                break;
+            }
+        }
+        for (j = 0;  j < size;  j++) {
+            HAL_READ_UINT8(IIC0_MDBUF, _val);
+            val[i+j] = _val;
+        }
+    }
+    return true;
+}
+#endif // 405
+
 //--------------------------------------------------------------------------
 // End of var_misc.c
--- a/packages/io/flash/current/ChangeLog
+++ b/packages/io/flash/current/ChangeLog
@@ -1,3 +1,10 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/flash.c: 
+	* include/flash.h: 
+	* cdl/io_flash.cdl: Add support for NAND (indirectly accessed)
+	devices.  This includes a generic "flash_read_buf()" function.
+
 2003-04-14  Jani Monoses  <jani@iv.ro>
 
 	* include/flash_dev.h: Include <cyg/infra/cyg_type.h> 
--- a/packages/io/flash/current/cdl/io_flash.cdl
+++ b/packages/io/flash/current/cdl/io_flash.cdl
@@ -9,6 +9,7 @@
 ## -------------------------------------------
 ## This file is part of eCos, the Embedded Configurable Operating System.
 ## Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+## Copyright (C) 2003 Gary Thomas
 ##
 ## eCos is free software; you can redistribute it and/or modify it under
 ## the terms of the GNU General Public License as published by the Free
@@ -105,6 +106,27 @@ cdl_package CYGPKG_IO_FLASH {
             locking (write-protection) of individual blocks."
     }
 
+    cdl_option CYGSEM_IO_FLASH_READ_INDIRECT {
+        display       "Hardware cannot support direct access to FLASH memory"
+        flavor        bool
+        default_value 0
+        requires      { !CYGSEM_IO_FLASH_VERIFY_PROGRAM }
+        description   "
+            This option will be asserted by devices which cannot support
+            direct access to the FLASH memory contents (e.g. EEPROM or NAND
+            devices).  In these cases, the driver must provide an appropriate
+            hardware access function."
+    }
+
+    cdl_option CYGSEM_IO_FLASH_CHATTER {
+        display          "Display status messages during flash operations"
+        flavor           bool
+        default_value    1
+        description      "
+           Selecting this option will cause the drivers to print status
+           messages as various flash operations are undertaken."
+    }
+
     cdl_option CYGSEM_IO_FLASH_VERIFY_PROGRAM {
         display          "Verify data programmed to flash"
         flavor           bool
@@ -113,6 +135,7 @@ cdl_package CYGPKG_IO_FLASH {
            Selecting this option will cause verification of data
            programmed to flash."
     }
+
     cdl_option CYGSEM_IO_FLASH_SOFT_WRITE_PROTECT {
         display          "Platform has flash soft DIP switch write-protect"
         flavor           bool
@@ -122,6 +145,7 @@ cdl_package CYGPKG_IO_FLASH {
            dipswitch to be read by software to determine whether the flash is
            write-protected or not."
     }
+
     cdl_component CYGPKG_IO_FLASH_BLOCK_DEVICE {
         display         "Instantiate in I/O block device API"
         flavor          bool
--- a/packages/io/flash/current/include/flash.h
+++ b/packages/io/flash/current/include/flash.h
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -63,6 +64,7 @@ typedef int _printf(const char *fmt, ...
 externC int flash_init(void *work_space, int work_space_length, _printf *pf);
 externC int flash_erase(void *base, int len, void **err_address);
 externC int flash_program(void *flash_base, void *ram_base, int len, void **err_address);
+externC int flash_read(void *flash_base, void *ram_base, int len, void **err_address);
 externC void flash_dev_query(void *data);
 #ifdef CYGHWR_IO_FLASH_BLOCK_LOCKING
 externC int flash_lock(void *base, int len, void **err_address);
--- a/packages/io/flash/current/src/flash.c
+++ b/packages/io/flash/current/src/flash.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -210,16 +211,18 @@ flash_erase(void *addr, int len, void **
         end_addr = (unsigned short *) ((CYG_ADDRESS) flash_info.end - 1);
     }
 
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("... Erase from %p-%p: ", (void*)block, (void*)end_addr);
+#endif
 
     HAL_FLASH_CACHES_OFF(d_cache, i_cache);
     FLASH_Enable(block, end_addr);
     while (block < end_addr) {
         // Supply the blocksize for a gross check for erase success
+#if !defined(CYGSEM_IO_FLASH_READ_INDIRECT)
         int i;
         unsigned char *dp;
         bool erased = true;
-        unsigned short *tmp_block;
 
         dp = (unsigned char *)block;
         for (i = 0;  i < flash_info.block_size;  i++) {
@@ -228,6 +231,11 @@ flash_erase(void *addr, int len, void **
                 break;
             }
         }
+#else
+        bool erased = false;
+#endif
+        unsigned short *tmp_block;
+
         if (!erased) {
             stat = (*_flash_erase_block)(block, flash_info.block_size);
             stat = flash_hwr_map_error(stat);
@@ -246,11 +254,15 @@ flash_erase(void *addr, int len, void **
         else{
             block = tmp_block;
         }
+#ifdef CYGSEM_IO_FLASH_CHATTER
         (*flash_info.pf)(".");
+#endif
     }
     FLASH_Disable(block, end_addr);
     HAL_FLASH_CACHES_ON(d_cache, i_cache);
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("\n");
+#endif
     return (stat);
 }
 
@@ -291,8 +303,10 @@ flash_program(void *_addr, void *_data, 
     }
 #endif
 
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("... Program from %p-%p at %p: ", (void*)data, 
                      (void*)(((CYG_ADDRESS)data)+len), (void*)addr);
+#endif
 
     HAL_FLASH_CACHES_OFF(d_cache, i_cache);
     FLASH_Enable((unsigned short*)addr, (unsigned short *)(addr+len));
@@ -314,24 +328,125 @@ flash_program(void *_addr, void *_data, 
         if (0 == stat) // Claims to be OK
             if (memcmp(addr, data, size) != 0) {                
                 stat = 0x0BAD;
+#ifdef CYGSEM_IO_FLASH_CHATTER
                 (*flash_info.pf)("V");
+#endif
             }
 #endif
         if (stat) {
             *err_addr = (void *)addr;
             break;
         }
+#ifdef CYGSEM_IO_FLASH_CHATTER
         (*flash_info.pf)(".");
+#endif
         len -= size;
         addr += size/sizeof(*addr);
         data += size/sizeof(*data);
     }
     FLASH_Disable((unsigned short*)addr, (unsigned short *)(addr+len));
     HAL_FLASH_CACHES_ON(d_cache, i_cache);
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("\n");
+#endif
     return (stat);
 }
 
+int
+flash_read(void *_addr, void *_data, int len, void **err_addr)
+{
+#ifdef CYGSEM_IO_FLASH_READ_INDIRECT
+    int stat = 0;
+    int size;
+    typedef int code_fun(void *, void *, int, unsigned long, int);
+    code_fun *_flash_read_buf;
+    unsigned char *addr = (unsigned char *)_addr;
+    unsigned char *data = (unsigned char *)_data;
+    CYG_ADDRESS tmp;
+    int d_cache, i_cache;
+
+    if (!flash_info.init) {
+        return FLASH_ERR_NOT_INIT;
+    }
+
+#ifdef CYGSEM_IO_FLASH_SOFT_WRITE_PROTECT
+    if (plf_flash_query_soft_wp(addr,len))
+        return FLASH_ERR_PROTECT;
+#endif
+
+#ifdef CYGHWR_IO_FLASH_DEVICE_NOT_IN_RAM
+    {
+        CYG_ADDRESS code_len;
+        extern char flash_read_buf[], flash_read_buf_end[];
+        // Copy 'read' code to RAM for execution
+        code_len = (CYG_ADDRESS)&flash_read_buf_end - (CYG_ADDRESS)&flash_read_buf;
+        _flash_read_buf = (code_fun *)flash_info.work_space;
+        memcpy(_flash_read_buf, &flash_read_buf, code_len);
+    }
+#else
+    {
+        externC code_fun flash_read_buf;
+        _flash_read_buf = (code_fun*) __anonymizer(&flash_read_buf);
+    }
+#endif
+
+#ifdef CYGSEM_IO_FLASH_CHATTER
+    (*flash_info.pf)("... Read from %p-%p at %p: ", (void*)data, 
+                     (void*)(((CYG_ADDRESS)data)+len), (void*)addr);
+#endif
+
+    HAL_FLASH_CACHES_OFF(d_cache, i_cache);
+    FLASH_Enable((unsigned short*)addr, (unsigned short *)(addr+len));
+    while (len > 0) {
+        size = len;
+        if (size > flash_info.block_size) size = flash_info.block_size;
+
+        tmp = (CYG_ADDRESS)addr & ~flash_info.block_mask;
+        if (tmp) {
+                tmp = flash_info.block_size - tmp;
+                if (size>tmp) size = tmp;
+
+        }
+
+        stat = (*_flash_read_buf)(addr, data, size, 
+                                     flash_info.block_mask, flash_info.buffer_size);
+        stat = flash_hwr_map_error(stat);
+#ifdef CYGSEM_IO_FLASH_VERIFY_PROGRAM_
+        if (0 == stat) // Claims to be OK
+            if (memcmp(addr, data, size) != 0) {                
+                stat = 0x0BAD;
+#ifdef CYGSEM_IO_FLASH_CHATTER
+                (*flash_info.pf)("V");
+#endif
+            }
+#endif
+        if (stat) {
+            *err_addr = (void *)addr;
+            break;
+        }
+#ifdef CYGSEM_IO_FLASH_CHATTER
+        (*flash_info.pf)(".");
+#endif
+        len -= size;
+        addr += size/sizeof(*addr);
+        data += size/sizeof(*data);
+    }
+    FLASH_Disable((unsigned short*)addr, (unsigned short *)(addr+len));
+    HAL_FLASH_CACHES_ON(d_cache, i_cache);
+#ifdef CYGSEM_IO_FLASH_CHATTER
+    (*flash_info.pf)("\n");
+#endif
+    return (stat);
+#else // CYGSEM_IO_FLASH_READ_INDIRECT
+    // Direct access to FLASH memory is possible - just move the requested bytes
+    if (!flash_info.init) {
+        return FLASH_ERR_NOT_INIT;
+    }
+    memcpy(_data, _addr, len);
+    return FLASH_ERR_OK;
+#endif
+}
+
 #ifdef CYGHWR_IO_FLASH_BLOCK_LOCKING
 
 int
@@ -376,7 +491,9 @@ flash_lock(void *addr, int len, void **e
         end_addr = (unsigned short *) ((CYG_ADDRESS) flash_info.end - 1);
     }
 
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("... Lock from %p-%p: ", block, end_addr);
+#endif
 
     HAL_FLASH_CACHES_OFF(d_cache, i_cache);
     FLASH_Enable(block, end_addr);
@@ -398,11 +515,15 @@ flash_lock(void *addr, int len, void **e
         else{
             block = tmp_block;
         }
+#ifdef CYGSEM_IO_FLASH_CHATTER
         (*flash_info.pf)(".");
+#endif
     }
     FLASH_Disable(block, end_addr);
     HAL_FLASH_CACHES_ON(d_cache, i_cache);
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("\n");
+#endif
     return (stat);
 }
 
@@ -448,7 +569,9 @@ flash_unlock(void *addr, int len, void *
         end_addr = (unsigned short *) ((CYG_ADDRESS) flash_info.end - 1);
     }
 
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("... Unlock from %p-%p: ", block, end_addr);
+#endif
 
     HAL_FLASH_CACHES_OFF(d_cache, i_cache);
     FLASH_Enable(block, end_addr);
@@ -469,11 +592,15 @@ flash_unlock(void *addr, int len, void *
         else{
             block = tmp_block;
         }
+#ifdef CYGSEM_IO_FLASH_CHATTER
         (*flash_info.pf)(".");
+#endif
     }
     FLASH_Disable(block, end_addr);
     HAL_FLASH_CACHES_ON(d_cache, i_cache);
+#ifdef CYGSEM_IO_FLASH_CHATTER
     (*flash_info.pf)("\n");
+#endif
     return (stat);
 }
 #endif
--- a/packages/io/wallclock/current/ChangeLog
+++ b/packages/io/wallclock/current/ChangeLog
@@ -1,3 +1,8 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* tests/wallclock.cxx: Allow test to complete, even if it looses sync.
+	This is useful to determine how much drift is present.
+
 2003-03-25  Michael Checky <Michael_Checky@Thermoking.com>
 
 	* include/wallclock/wallclock.inl: Added parens to TO_BCD() and TO_DEC()
--- a/packages/io/wallclock/current/tests/wallclock.cxx
+++ b/packages/io/wallclock/current/tests/wallclock.cxx
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -104,6 +105,7 @@ void wallclock_thread( CYG_ADDRWORD id )
     cyg_uint32 base;
     cyg_uint32 wtime;
     cyg_tick_count ticks;
+    cyg_bool ok = true;
 
     CYG_TEST_INFO("Testing accuracy of wallclock (10 seconds silence)");
 
@@ -128,7 +130,7 @@ void wallclock_thread( CYG_ADDRWORD id )
         if(wtime != base+i)
         {
             diag_printf("offset %d, read %d, expected %d\n", i, wtime, base+i);
-            CYG_TEST_FAIL_FINISH( "Clock out of sync" );
+            ok = false;
         }
 
         // then calculate how much the above took so the delay
@@ -172,7 +174,10 @@ void wallclock_thread( CYG_ADDRWORD id )
         }
     }
 
-    CYG_TEST_PASS_FINISH("Wallclock OK");
+    if (ok)
+        CYG_TEST_PASS_FINISH("Wallclock OK");
+    else
+        CYG_TEST_FAIL_FINISH( "Clock out of sync" );
     
 }
 
--- a/packages/redboot/current/ChangeLog
+++ b/packages/redboot/current/ChangeLog
@@ -1,3 +1,27 @@
+2003-09-19  Gary Thomas  <gary@mlbassoc.com>
+
+	* src/net/tftp_client.c: Make timeout on very first transaction really
+	long - again since some servers are just slow/ill mannered.
+
+	* src/net/net_io.c: Allow default server IP to be always enabled, thus
+	it can override what is provided by BOOTP/DHCP (since some DHCP servers
+	don't provide this properly).
+
+	* src/time_date.cxx: New file - support "date" command for platforms
+	with battery backed up clocks.
+
+	* src/fconfig.c: New file - split out from flash.c
+
+	* src/main.c: 
+	* src/load.c: 
+	* src/flash.c: 
+	* src/alias.c: 
+	* include/redboot.h: 
+	* cdl/redboot.cdl: Support multiple "RAM" segments (known writable
+	memory).  Also rearrange FLASH & FCONFIG, separating them as much
+	as possible and supporting FCONFIG data stored in some other sort
+	of device, like EEPROM.
+
 2003-09-09  Gary Thomas  <gary@mlbassoc.com>
 
 	* src/flash.c (flash_config_insert_value): Default value was
--- a/packages/redboot/current/cdl/redboot.cdl
+++ b/packages/redboot/current/cdl/redboot.cdl
@@ -138,10 +138,24 @@ cdl_package CYGPKG_REDBOOT {
               to list previous commands. Also enables history expansion via '!'
               character similar to bash shell."
         }
+
+        cdl_option CYGBLD_REDBOOT_MAX_MEM_SEGMENTS {
+            display        "Number of unique RAM segments on platform"
+            flavor         data
+            default_value  1
+            description  "
+              Change this option to be the number of memory segments which are
+              supported by the platform.  If the value is greater than 1, then
+              a platform specific function must provide information about the
+              additional segments."
+        }
     
         cdl_option CYGBLD_BUILD_REDBOOT_WITH_ZLIB {
             display       "Include support gzip/zlib decompression"
             active_if     CYGPKG_COMPRESS_ZLIB
+## FIXME!
+            requires      { !CYGSEM_IO_FLASH_READ_INDIRECT }
+## FIXME!
             no_define
             default_value 1
             implements    CYGINT_COMPRESS_ZLIB_LOCAL_ALLOC
@@ -425,6 +439,18 @@ cdl_package CYGPKG_REDBOOT {
               and query the baud rate on the selected console."     
         }
     
+        cdl_option CYGSEM_REDBOOT_PLF_STARTUP {
+            display       "Run a platform specific startup function."
+            flavor        bool
+            default_value 0
+            description   "
+              If this option is enabled then RedBoot will execute a platform
+              specific startup function before entering into its command line
+              processing.  This allows the platform to perform any special
+              setups before RedBoot actually starts running.  Note: the entire
+              RedBoot environment will already be initialized at this point."
+        }
+    
         cdl_option CYGPKG_REDBOOT_MAX_CMD_LINE {
             display       "Maximum command line length"
             flavor        data
@@ -486,39 +512,6 @@ cdl_package CYGPKG_REDBOOT {
               into memory for execution or executed in place."
             compile -library=libextras.a flash.c
     
-            cdl_option CYGBLD_REDBOOT_MIN_IMAGE_SIZE {
-                display       "Minimum image size"
-                flavor        data
-                default_value 0x20000
-                description "
-                  This option controls the minimum length of images kept by
-                  the FIS.  In particular, it should be large enough to hold
-                  the RedBoot primary image itself, as well as be a natural
-                  multiple of the FLASH erase block size."
-            }
-    
-            cdl_option CYGBLD_REDBOOT_FLASH_BOOT_OFFSET {
-                display       "Offset from start of FLASH to RedBoot boot image"
-                flavor        data
-                default_value CYGNUM_REDBOOT_FLASH_RESERVED_BASE
-                requires      { CYGNUM_REDBOOT_FLASH_RESERVED_BASE <= \
-                                CYGBLD_REDBOOT_FLASH_BOOT_OFFSET }
-                description "
-                  This option controls where the RedBoot boot image is located
-                  relative to the start of FLASH."
-            }
-    
-            cdl_option CYGNUM_REDBOOT_FLASH_RESERVED_BASE {
-                display       "Size of reserved area at start of FLASH"
-                flavor        data
-                default_value 0
-                description "
-                  This option reserves an area at the start of FLASH where RedBoot
-                  will never interfere; it is expected that this area contains
-                  (non-RedBoot-based) POST code or some other boot monitor that
-                  executes before RedBoot."
-            }
-    
             cdl_option CYGOPT_REDBOOT_FIS {
                 display         "RedBoot Flash Image System support"
                 default_value   1
@@ -628,89 +621,38 @@ cdl_package CYGPKG_REDBOOT {
                       to reduce this value in order to get more slots in
                       the FIS directory."
                 }
-            }
     
-            cdl_component CYGSEM_REDBOOT_FLASH_CONFIG {
-                display       "Keep RedBoot configuration data in FLASH"
-                flavor        bool
-                default_value 1
-                description "
-                  When this option is enabled, RedBoot will keep configuration
-                  data in a separate block of FLASH memory.  This data will
-                  include such items as the node IP address or startup scripts."
-    
-                cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
-                    display       "Length of configuration data in FLASH"
+                cdl_option CYGBLD_REDBOOT_MIN_IMAGE_SIZE {
+                    display       "Minimum image size"
                     flavor        data
-                    default_value 4096
+                    default_value 0x20000
                     description "
-                      This option is used to control the amount of memory and FLASH
-                      to be used for configuration options (persistent storage)."
+                      This option controls the minimum length of images kept by
+                      the FIS.  In particular, it should be large enough to hold
+                      the RedBoot primary image itself, as well as be a natural
+                      multiple of the FLASH erase block size."
                 }
-    
-                cdl_option CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG {
-                    display       "Merged config data and FIS directory"
-                    flavor        bool              
-                    active_if     CYGOPT_REDBOOT_FIS
+        
+                cdl_option CYGBLD_REDBOOT_FLASH_BOOT_OFFSET {
+                    display       "Offset from start of FLASH to RedBoot boot image"
+                    flavor        data
+                    default_value CYGNUM_REDBOOT_FLASH_RESERVED_BASE
+                    requires      { CYGNUM_REDBOOT_FLASH_RESERVED_BASE <= \
+                                    CYGBLD_REDBOOT_FLASH_BOOT_OFFSET }
+                    description "
+                      This option controls where the RedBoot boot image is located
+                      relative to the start of FLASH."
+                }
+        
+                cdl_option CYGNUM_REDBOOT_FLASH_RESERVED_BASE {
+                    display       "Size of reserved area at start of FLASH"
+                    flavor        data
                     default_value 0
                     description "
-                      If this option is set, then the FIS directory and FLASH 
-                      configuration database will be stored in the same physical
-                      FLASH block."
-                }
-    
-                cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK {
-                    display       "Which block of flash to use" 
-                    flavor         data
-                    default_value  (-2)
-                    description "
-                      Which block of flash should hold the configuration 
-                      information. Positive numbers are absolute block numbers. 
-                      Negative block numbers count backwards from the last block.
-                      eg 2 means block 2, -2 means the last but one block."
-                }
-    
-                cdl_option CYGSEM_REDBOOT_FLASH_ALIASES {
-                    display       "Support simple macros/aliases in FLASH"
-                    flavor        bool
-                    default_value 1
-                    description "
-                      This option is used to allow support for simple text-based
-                      macros (aliases).  These aliases are kept in the FLASH
-                      configuration data (persistent storage)."
-                }
-    
-                cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
-                    display       "Length of strings in FLASH configuration data"
-                    flavor        data
-                    default_value 128
-                    description "
-                      This option is used to control the amount of memory and FLASH
-                      to be used for string configuration options (persistent storage)."
-                }
-    
-                cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
-                    display       "Length of configuration script(s) in FLASH"
-                    flavor        data
-                    default_value 512
-                    description "
-                      This option is used to control the amount of memory and FLASH
-                      to be used for configuration options (persistent storage)."
-                }
-    
-                cdl_option CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK {
-                    display       "Fallback to read-only FLASH configuration"
-                    flavor        bool
-                    default_value 1
-                    description "
-                      This option will cause the configuration information to
-                      revert to the readonly information stored in the FLASH.
-                      The option only takes effect after 
-                        1) the config_ok flag has been set to be true,
-                           indicating that at one time the copy in RAM was valid;
-                      and
-                        2) the information in RAM has been verified to be invalid"
-                      
+                      This option reserves an area at the start of FLASH where RedBoot
+                      will never interfere; it is expected that this area contains
+                      (non-RedBoot-based) POST code or some other boot monitor that
+                      executes before RedBoot."
                 }
             }
     
@@ -753,6 +695,104 @@ cdl_package CYGPKG_REDBOOT {
             }
         }
     
+        cdl_component CYGSEM_REDBOOT_FLASH_CONFIG {
+            display       "Keep RedBoot configuration data in FLASH"
+            flavor        bool
+            default_value 1
+            compile       fconfig.c
+            description "
+              When this option is enabled, RedBoot will keep configuration
+              data in a separate block of FLASH memory.  This data will
+              include such items as the node IP address or startup scripts."
+
+            cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_SIZE {
+                display       "Length of configuration data in FLASH"
+                flavor        data
+                default_value 4096
+                description "
+                  This option is used to control the amount of memory and FLASH
+                  to be used for configuration options (persistent storage)."
+            }
+
+            cdl_option CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA {
+                display       "Style of media used for persistent data storage"
+                flavor        data
+                legal_values  { "FLASH" "EEPROM" }
+                default_value { "FLASH" }
+#                requires      { ((CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA == "FLASH") && CYGOPT_REDBOOT_FIS) ||
+#                                ((CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA == "EEPROM") && !CYGOPT_REDBOOT_FIS) }
+                description "
+                  Persistent data storage can either be held in 'norma' FLASH
+                  or some other device (represented by the 'EEPROM' choice).
+                  The different styles utilize different access methods."
+            }
+
+            cdl_option CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG {
+                display       "Merged config data and FIS directory"
+                flavor        bool              
+                active_if     { CYGOPT_REDBOOT_FIS && (CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA == "FLASH") }
+                default_value 0
+                description "
+                  If this option is set, then the FIS directory and FLASH 
+                  configuration database will be stored in the same physical
+                  FLASH block."
+            }
+
+            cdl_option CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK {
+                display       "Which block of flash to use" 
+                flavor         data
+                default_value  (-2)
+                description "
+                  Which block of flash should hold the configuration 
+                  information. Positive numbers are absolute block numbers. 
+                  Negative block numbers count backwards from the last block.
+                  eg 2 means block 2, -2 means the last but one block."
+            }
+
+            cdl_option CYGSEM_REDBOOT_FLASH_ALIASES {
+                display       "Support simple macros/aliases in FLASH"
+                flavor        bool
+                default_value 1
+                description "
+                  This option is used to allow support for simple text-based
+                  macros (aliases).  These aliases are kept in the FLASH
+                  configuration data (persistent storage)."
+            }
+
+            cdl_option CYGNUM_REDBOOT_FLASH_STRING_SIZE {
+                display       "Length of strings in FLASH configuration data"
+                flavor        data
+                default_value 128
+                description "
+                  This option is used to control the amount of memory and FLASH
+                  to be used for string configuration options (persistent storage)."
+            }
+
+            cdl_option CYGNUM_REDBOOT_FLASH_SCRIPT_SIZE {
+                display       "Length of configuration script(s) in FLASH"
+                flavor        data
+                default_value 512
+                description "
+                  This option is used to control the amount of memory and FLASH
+                  to be used for configuration options (persistent storage)."
+            }
+
+            cdl_option CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK {
+                display       "Fallback to read-only FLASH configuration"
+                flavor        bool
+                default_value { (CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA == "FLASH") }
+                description "
+                  This option will cause the configuration information to
+                  revert to the readonly information stored in the FLASH.
+                  The option only takes effect after 
+                    1) the config_ok flag has been set to be true,
+                       indicating that at one time the copy in RAM was valid;
+                  and
+                    2) the information in RAM has been verified to be invalid"
+                  
+            }
+        }
+    
         cdl_component CYGPKG_REDBOOT_DISK {
             display       "Allow RedBoot to support disks"
             flavor        bool
@@ -856,6 +896,16 @@ cdl_package CYGPKG_REDBOOT {
             }
         }
     
+        cdl_option CYGSEM_REDBOOT_RTC {
+            display      "Support RTC for time & date functions"
+            active_if    { CYGPKG_IO_WALLCLOCK }
+            default_value 1
+            description  "
+              When this option is enabled, RedBoot will support commands to
+              query and set the real time clock (time and date)"
+            compile -library=libextras.a time_date.cxx
+        }
+    
         cdl_option CYGPRI_REDBOOT_ROM_MONITOR {
             display      "Behave like a ROM monitor"
             active_if    { CYG_HAL_STARTUP == "ROM" || CYG_HAL_STARTUP == "ROMRAM" }
--- a/packages/redboot/current/include/flash_config.h
+++ b/packages/redboot/current/include/flash_config.h
@@ -94,4 +94,13 @@ bool flash_get_config(char *key, void *v
 // if no space is available.
 bool flash_add_config(struct config_option *opt, bool update);
 
+// Internal structure used to hold config data
+struct _config {
+    unsigned long len;
+    unsigned long key1;
+    unsigned char config_data[MAX_CONFIG_DATA-(4*4)];
+    unsigned long key2;
+    unsigned long cksum;
+};
+
 #endif // _FLASH_CONFIG_H_
--- a/packages/redboot/current/include/redboot.h
+++ b/packages/redboot/current/include/redboot.h
@@ -82,7 +82,12 @@ EXTERN int argc;
 #define MAX_ARGV 16
 EXTERN char *argv[MAX_ARGV];
 EXTERN unsigned char *ram_start, *ram_end;
-EXTERN unsigned char *user_ram_start, *user_ram_end;
+EXTERN struct _mem_segment {
+    unsigned char *start, *end;
+} mem_segments[CYGBLD_REDBOOT_MAX_MEM_SEGMENTS];
+#define NO_MEMORY (unsigned char *)0xFFFFFFFF
+EXTERN bool valid_address(unsigned char *addr);
+EXTERN void cyg_plf_memory_segment(int seg, unsigned char **start, unsigned char **end);
 EXTERN unsigned char *workspace_start, *workspace_end;
 EXTERN unsigned long workspace_size;
 
@@ -120,6 +125,10 @@ EXTERN int console_baud_rate;
 EXTERN unsigned char *fis_zlib_common_buffer;
 #endif
 
+#ifdef CYGSEM_REDBOOT_PLF_STARTUP
+EXTERN void cyg_plf_redboot_startup(void);
+#endif
+
 // Prototypes
 typedef int _printf_fun(const char *fmt, ...);
 externC int  strcasecmp(const char *s1, const char *s2);
--- a/packages/redboot/current/src/alias.c
+++ b/packages/redboot/current/src/alias.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -68,10 +69,10 @@ static char *
 lookup_alias(char *alias, char *alias_buf)
 {
     if (0 == strcasecmp("FREEMEMLO", alias)) {
-        diag_sprintf(alias_buf,"%p", ((CYG_ADDRWORD)user_ram_start + 0x03ff) & ~0x03ff);
+        diag_sprintf(alias_buf,"%p", ((CYG_ADDRWORD)mem_segments[0].start + 0x03ff) & ~0x03ff);
         return alias_buf;
     } else if (0 == strcasecmp("FREEMEMHI", alias)) {
-        diag_sprintf(alias_buf,"%p", ((CYG_ADDRWORD)user_ram_end) & ~0x03ff);
+        diag_sprintf(alias_buf,"%p", ((CYG_ADDRWORD)mem_segments[0].end) & ~0x03ff);
         return alias_buf;
     }
 
new file mode 100644
--- /dev/null
+++ b/packages/redboot/current/src/fconfig.c
@@ -0,0 +1,1015 @@
+//==========================================================================
+//
+//      fconfig.c
+//
+//      RedBoot - persistent data storage support (FLASH or EEPROM)
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas
+// Contributors: gthomas, tkoeller
+// Date:         2000-07-28
+// Purpose:      
+// Description:  
+//              
+// This code is part of RedBoot (tm).
+//
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <redboot.h>
+#include <cyg/io/flash.h>
+#include <fis.h>
+
+#ifdef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
+// Note horrid intertwining of functions, to save precious FLASH
+#endif
+
+#ifdef CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_EEPROM
+externC void write_eeprom(void *buf, int len);
+externC void read_eeprom(void *buf, int len);
+#endif
+
+// Round a quantity up
+#define _rup(n,s) ((((n)+(s-1))/s)*s)
+
+#include <flash_config.h>
+
+// Configuration data, saved in FLASH, used to set/update RedBoot
+// normal "configuration" data items.
+struct _config *config, *backup_config;
+
+// Local data used by these routines
+#ifdef CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH
+extern void *flash_start, *flash_end;
+extern int flash_block_size, flash_num_blocks;
+extern int __flash_init;
+#ifdef CYGOPT_REDBOOT_FIS
+extern void *fis_work_block;
+extern void *fis_addr;
+extern int fisdir_size;  // Size of FIS directory.
+#endif
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
+static struct _config  *readonly_config;
+#endif
+void *cfg_base;   // Location in Flash of config data
+int   cfg_size;   // Length of config data - rounded to Flash block size
+#endif // FLASH MEDIA
+
+// Prototypes for local functions
+static unsigned char *flash_lookup_config(char *key);
+
+static bool config_ok;
+
+#define CONFIG_KEY1    0x0BADFACE
+#define CONFIG_KEY2    0xDEADDEAD
+
+#define CONFIG_DONE    0
+#define CONFIG_ABORT  -1
+#define CONFIG_CHANGED 1
+#define CONFIG_OK      2
+#define CONFIG_BACK    3
+#define CONFIG_BAD     4
+
+// Note: the following options are related.  If 'boot_script' is false, then
+// the other values are used in the configuration.  Because of the way
+// that configuration tables are generated, they should have names which
+// are related.  The configuration options will show up lexicographically
+// ordered, thus the peculiar naming.
+RedBoot_config_option("Run script at boot",
+                      boot_script,
+                      ALWAYS_ENABLED, true,
+                      CONFIG_BOOL,
+                      false
+    );
+RedBoot_config_option("Boot script",
+                      boot_script_data,
+                      "boot_script", true,
+                      CONFIG_SCRIPT,
+                      ""
+    );
+// Some preprocessor magic for building the [constant] prompt string
+#define __cat(s1,c2,s3) s1 #c2 s3
+#define _cat(s1,c2,s3) __cat(s1,c2,s3)
+RedBoot_config_option(_cat("Boot script timeout (",
+                           CYGNUM_REDBOOT_BOOT_SCRIPT_TIMEOUT_RESOLUTION,
+                           "ms resolution)"),
+                      boot_script_timeout,
+                      "boot_script", true,
+                      CONFIG_INT,
+                      0
+    );
+#undef __cat
+#undef _cat
+
+#ifdef CYGSEM_REDBOOT_VARIABLE_BAUD_RATE
+RedBoot_config_option("Console baud rate",
+                      console_baud_rate,
+                      ALWAYS_ENABLED, true,
+                      CONFIG_INT,
+                      CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD
+    );
+#endif
+
+CYG_HAL_TABLE_BEGIN( __CONFIG_options_TAB__, RedBoot_config_options);
+CYG_HAL_TABLE_END( __CONFIG_options_TAB_END__, RedBoot_config_options);
+
+extern struct config_option __CONFIG_options_TAB__[], __CONFIG_options_TAB_END__[];
+
+// 
+// Layout of config data
+// Each data item is variable length, with the name, type and dependencies
+// encoded into the object.
+//  offset   contents
+//       0   data type
+//       1   length of name (N)
+//       2   enable sense
+//       3   length of enable key (M)
+//       4   key name
+//     N+4   enable key
+//   M+N+4   data value
+//
+
+#define CONFIG_OBJECT_TYPE(dp)          (dp)[0]
+#define CONFIG_OBJECT_KEYLEN(dp)        (dp)[1]
+#define CONFIG_OBJECT_ENABLE_SENSE(dp)  (dp)[2]
+#define CONFIG_OBJECT_ENABLE_KEYLEN(dp) (dp)[3]
+#define CONFIG_OBJECT_KEY(dp)           ((dp)+4)
+#define CONFIG_OBJECT_ENABLE_KEY(dp)    ((dp)+4+CONFIG_OBJECT_KEYLEN(dp))
+#define CONFIG_OBJECT_VALUE(dp)         ((dp)+4+CONFIG_OBJECT_KEYLEN(dp)+CONFIG_OBJECT_ENABLE_KEYLEN(dp))
+
+#define LIST_OPT_LIST_ONLY (1)
+#define LIST_OPT_NICKNAMES (2)
+#define LIST_OPT_FULLNAMES (4)
+#define LIST_OPT_DUMBTERM  (8)
+
+static void config_init(void);
+
+static int
+get_config(unsigned char *dp, char *title, int list_opt, char *newvalue )
+{
+    char line[256], hold_line[256], *sp, *lp;
+    int ret;
+    bool hold_bool_val, new_bool_val, enable;
+    unsigned long hold_int_val, new_int_val;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    in_addr_t hold_ip_val, new_ip_val;
+    enet_addr_t hold_esa_val;
+    int esa_ptr;
+    char *esp;
+#endif
+    void *val_ptr;
+    int type;
+
+    if (CONFIG_OBJECT_ENABLE_KEYLEN(dp)) {
+        flash_get_config(CONFIG_OBJECT_ENABLE_KEY(dp), &enable, CONFIG_BOOL);
+        if (((bool)CONFIG_OBJECT_ENABLE_SENSE(dp) && !enable) ||
+            (!(bool)CONFIG_OBJECT_ENABLE_SENSE(dp) && enable)) {
+            return CONFIG_OK;  // Disabled field
+        }
+    }
+    lp = line;  *lp = '\0';
+    val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
+    if (LIST_OPT_NICKNAMES & list_opt)
+        diag_printf("%s: ", CONFIG_OBJECT_KEY(dp));
+    if (LIST_OPT_FULLNAMES & list_opt) {
+        if (title != (char *)NULL) {
+            diag_printf("%s: ", title);
+        } else {
+            diag_printf("%s: ", CONFIG_OBJECT_KEY(dp));
+        }
+    }
+    switch (type = CONFIG_OBJECT_TYPE(dp)) {
+    case CONFIG_BOOL:
+        memcpy(&hold_bool_val, val_ptr, sizeof(bool));
+        lp += diag_sprintf(lp, "%s", hold_bool_val ? "true" : "false");
+        break;
+    case CONFIG_INT:
+        memcpy(&hold_int_val, val_ptr, sizeof(unsigned long));
+        lp += diag_sprintf(lp, "%ld", hold_int_val);
+        break;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    case CONFIG_IP:
+        lp += diag_sprintf(lp, "%s", inet_ntoa((in_addr_t *)val_ptr));
+        if (0 == strcmp("0.0.0.0", line) && !(LIST_OPT_LIST_ONLY & list_opt)) {
+            // then we have a deeply unhelpful starting text - kill it off
+            // (unless we are just listing all values)
+            lp = line;  *lp = '\0';
+        }
+        break;
+    case CONFIG_ESA:
+        for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
+            lp += diag_sprintf(lp, "0x%02X", ((unsigned char *)val_ptr)[esa_ptr]);
+            if (esa_ptr < (sizeof(enet_addr_t)-1)) lp += diag_sprintf(lp, ":");
+        }
+        break;
+#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
+    case CONFIG_NETPORT:
+        lp += diag_sprintf(lp, "%s", (unsigned char *)val_ptr);
+        break;
+#endif
+#endif
+    case CONFIG_STRING:
+        lp += diag_sprintf(lp, "%s", (unsigned char *)val_ptr);
+        break;
+    case CONFIG_SCRIPT:
+        diag_printf("\n");
+        sp = lp = (unsigned char *)val_ptr;
+        while (*sp) {
+            while (*lp != '\n') lp++;
+            *lp = '\0';
+            diag_printf(".. %s\n", sp);
+            *lp++ = '\n';
+            sp = lp;
+        }
+        break;
+    }
+    if (LIST_OPT_LIST_ONLY & list_opt) {
+        diag_printf("%s\n", line);
+        return CONFIG_OK;
+    }
+    if (type != CONFIG_SCRIPT) {
+        if (NULL != newvalue) {
+            ret = strlen(newvalue);
+            if (ret > sizeof(line))
+                return CONFIG_BAD;
+            strcpy(hold_line, line); // Hold the old value for comparison
+            strcpy(line, newvalue);
+            diag_printf("Setting to %s\n", newvalue);
+        } else {
+            // read from terminal
+            strcpy(hold_line, line);
+            if (LIST_OPT_DUMBTERM & list_opt) {
+                diag_printf( (CONFIG_STRING == type ?
+                              "%s > " :
+                              "%s ? " ), line);
+                *line = '\0';
+            }
+            ret = _rb_gets_preloaded(line, sizeof(line), 0);
+        }
+        if (ret < 0) return CONFIG_ABORT;
+        // empty input - leave value untouched (else DNS goes away for a
+        // minute to try to look it up) but we must accept empty value for strings.
+        if (0 == line[0] && CONFIG_STRING != type) return CONFIG_OK; 
+        if (strcmp(line, hold_line) == 0) return CONFIG_OK;  // Just a CR - leave value untouched
+        lp = &line[strlen(line)-1];
+        if (*lp == '.') return CONFIG_DONE;
+        if (*lp == '^') return CONFIG_BACK;
+    }
+    switch (type) {
+    case CONFIG_BOOL:
+        memcpy(&hold_bool_val, val_ptr, sizeof(bool));
+        if (!parse_bool(line, &new_bool_val)) {
+            return CONFIG_BAD;
+        }
+        if (hold_bool_val != new_bool_val) {
+            memcpy(val_ptr, &new_bool_val, sizeof(bool));
+            return CONFIG_CHANGED;
+        } else {
+            return CONFIG_OK;
+        }
+        break;
+    case CONFIG_INT:
+        memcpy(&hold_int_val, val_ptr, sizeof(unsigned long));
+        if (!parse_num(line, &new_int_val, 0, 0)) {
+            return CONFIG_BAD;
+        }
+        if (hold_int_val != new_int_val) {
+            memcpy(val_ptr, &new_int_val, sizeof(unsigned long));
+            return CONFIG_CHANGED;
+        } else {
+            return CONFIG_OK;
+        }
+        break;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    case CONFIG_IP:
+        memcpy(&hold_ip_val.s_addr, &((in_addr_t *)val_ptr)->s_addr, sizeof(in_addr_t));
+        if (!_gethostbyname(line, &new_ip_val)) {
+            return CONFIG_BAD;
+        }
+        if (hold_ip_val.s_addr != new_ip_val.s_addr) {
+            memcpy(val_ptr, &new_ip_val, sizeof(in_addr_t));
+            return CONFIG_CHANGED;
+        } else {
+            return CONFIG_OK;
+        }
+        break;
+    case CONFIG_ESA:
+        memcpy(&hold_esa_val, val_ptr, sizeof(enet_addr_t));
+        esp = line;
+        for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
+            unsigned long esa_byte;
+            if (!parse_num(esp, &esa_byte, &esp, ":")) {
+                memcpy(val_ptr, &hold_esa_val, sizeof(enet_addr_t));
+                return CONFIG_BAD;
+            }
+            ((unsigned char *)val_ptr)[esa_ptr] = esa_byte;
+        }
+        return CONFIG_CHANGED;
+        break;
+#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
+    case CONFIG_NETPORT:
+	if (strlen(line) >= MAX_STRING_LENGTH || net_devindex(line) < 0) {
+	    int index;
+	    const char *name;
+	    diag_printf("Sorry, Port name must be one of:\n");
+	    for (index = 0; (name = net_devname(index)) != NULL; index++)
+		diag_printf("    %s\n", name);
+            return CONFIG_BAD;
+	}
+        strcpy((unsigned char *)val_ptr, line);
+	break;
+#endif
+#endif
+    case CONFIG_SCRIPT:
+        // Assume it always changes
+        sp = (unsigned char *)val_ptr;
+        diag_printf("Enter script, terminate with empty line\n");
+        while (true) {
+            *sp = '\0';
+            diag_printf(">> ");
+            ret = _rb_gets(line, sizeof(line), 0);
+            if (ret < 0) return CONFIG_ABORT;
+            if (strlen(line) == 0) break;
+            lp = line;
+            while (*lp) {
+                *sp++ = *lp++;
+            }
+            *sp++ = '\n';
+        }
+        break;
+    case CONFIG_STRING:
+        if (strlen(line) >= MAX_STRING_LENGTH) {
+            diag_printf("Sorry, value is too long\n");
+            return CONFIG_BAD;
+        }
+        strcpy((unsigned char *)val_ptr, line);
+        break;
+    }
+    return CONFIG_CHANGED;
+}
+
+//
+// Manage configuration information with the FLASH
+//
+
+static int
+config_length(int type)
+{
+    switch (type) {
+    case CONFIG_BOOL:
+        return sizeof(bool);
+    case CONFIG_INT:
+        return sizeof(unsigned long);
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    case CONFIG_IP:
+        return sizeof(in_addr_t);
+    case CONFIG_ESA:
+        // Would like this to be sizeof(enet_addr_t), but that causes much
+        // pain since it fouls the alignment of data which follows.
+        return 8;
+#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
+    case CONFIG_NETPORT:
+        return MAX_STRING_LENGTH;
+#endif
+#endif
+    case CONFIG_STRING:
+        return MAX_STRING_LENGTH;
+    case CONFIG_SCRIPT:
+        return MAX_SCRIPT_LENGTH;
+    default:
+        return 0;
+    }
+}
+
+static cmd_fun do_flash_config;
+RedBoot_cmd("fconfig",
+            "Manage configuration kept in FLASH memory",
+            "[-i] [-l] [-n] [-f] [-d] | [-d] nickname [value]",
+            do_flash_config
+    );
+
+static void
+do_flash_config(int argc, char *argv[])
+{
+    bool need_update = false;
+    struct config_option *optend = __CONFIG_options_TAB_END__;
+    struct config_option *opt = __CONFIG_options_TAB__;
+    struct option_info opts[5];
+    bool list_only;
+    bool nicknames;
+    bool fullnames;
+    bool dumbterminal;
+    int list_opt = 0;
+    unsigned char *dp;
+    int len, ret;
+    char *title;
+    char *onlyone = NULL;
+    char *onevalue = NULL;
+    bool doneone = false;
+    bool init = false;
+
+#ifdef CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH
+    if (!__flash_init) {
+        diag_printf("Sorry, no FLASH memory is available\n");
+        return;
+    }
+#endif
+    memcpy(backup_config, config, sizeof(struct _config));
+    script = (unsigned char *)0;
+
+    init_opts(&opts[0], 'l', false, OPTION_ARG_TYPE_FLG, 
+              (void **)&list_only, (bool *)0, "list configuration only");
+    init_opts(&opts[1], 'n', false, OPTION_ARG_TYPE_FLG, 
+              (void **)&nicknames, (bool *)0, "show nicknames");
+    init_opts(&opts[2], 'f', false, OPTION_ARG_TYPE_FLG, 
+              (void **)&fullnames, (bool *)0, "show full names");
+    init_opts(&opts[3], 'i', false, OPTION_ARG_TYPE_FLG, 
+              (void **)&init, (bool *)0, "initialize configuration database");
+    init_opts(&opts[4], 'd', false, OPTION_ARG_TYPE_FLG, 
+              (void **)&dumbterminal, (bool *)0, "dumb terminal: no clever edits");
+
+    // First look to see if we are setting or getting a single option
+    // by just quoting its nickname
+    if ( (2 == argc && '-' != argv[1][0]) ||
+         (3 == argc && '-' != argv[1][0] && '-' != argv[2][0])) {
+        // then the command was "fconfig foo [value]"
+        onlyone = argv[1];
+        onevalue = (3 == argc) ? argv[2] : NULL;
+        list_opt = LIST_OPT_NICKNAMES;
+    }
+    // Next see if we are setting or getting a single option with a dumb
+    // terminal invoked, ie. no line editing.
+    else if (3 == argc &&
+             '-' == argv[1][0] && 'd' == argv[1][1] && 0 == argv[1][2] && 
+             '-' != argv[2][0]) {
+        // then the command was "fconfig -d foo"
+        onlyone = argv[2];
+        onevalue = NULL;
+        list_opt = LIST_OPT_NICKNAMES | LIST_OPT_DUMBTERM;
+    }
+    else {
+        if (!scan_opts(argc, argv, 1, opts, 5, 0, 0, ""))
+            return;
+        list_opt |= list_only ? LIST_OPT_LIST_ONLY : 0;
+        list_opt |= nicknames ? LIST_OPT_NICKNAMES : LIST_OPT_FULLNAMES;
+        list_opt |= fullnames ? LIST_OPT_FULLNAMES : 0;
+        list_opt |= dumbterminal ? LIST_OPT_DUMBTERM : 0;
+    }
+
+    if (init && verify_action("Initialize non-volatile configuration")) {
+        config_init();
+        need_update = true;
+    }
+
+    dp = &config->config_data[0];
+    while (dp < &config->config_data[sizeof(config->config_data)]) {
+        if (CONFIG_OBJECT_TYPE(dp) == CONFIG_EMPTY) {
+            break;
+        }
+        len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) + 
+            config_length(CONFIG_OBJECT_TYPE(dp));
+        // Provide a title for well known [i.e. builtin] objects
+        title = (char *)NULL;
+        opt = __CONFIG_options_TAB__;
+        while (opt != optend) {
+            if (strcmp(opt->key, CONFIG_OBJECT_KEY(dp)) == 0) {
+                title = opt->title;
+                break;
+            }
+            opt++;
+        }
+        if ( onlyone && 0 != strcmp(CONFIG_OBJECT_KEY(dp), onlyone) )
+            ret = CONFIG_OK; // skip this entry
+        else {
+            doneone = true;
+            ret = get_config(dp, title, list_opt, onevalue); // do this opt
+        }
+        switch (ret) {
+        case CONFIG_DONE:
+            goto done;
+        case CONFIG_ABORT:
+            memcpy(config, backup_config, sizeof(struct _config));
+            return;
+        case CONFIG_CHANGED:
+            need_update = true;
+        case CONFIG_OK:
+            dp += len;
+            break;
+        case CONFIG_BACK:
+            dp = &config->config_data[0];
+            continue;
+        case CONFIG_BAD:
+            // Nothing - make him do it again
+            diag_printf ("** invalid entry\n");
+            onevalue = NULL; // request a good value be typed in - or abort/whatever
+        }
+    }
+
+ done:
+    if (NULL != onlyone && !doneone) {
+#ifdef CYGSEM_REDBOOT_ALLOW_DYNAMIC_FLASH_CONFIG_DATA
+        if (verify_action("** entry '%s' not found - add", onlyone)) {
+            struct config_option opt;
+            diag_printf("Trying to add value\n");
+        }
+#else
+        diag_printf("** entry '%s' not found", onlyone);
+#endif
+    }
+    if (!need_update)
+        return;
+    flash_write_config();
+}
+
+
+#ifdef CYGSEM_REDBOOT_FLASH_ALIASES
+static cmd_fun do_alias;
+RedBoot_cmd("alias",
+            "Manage aliases kept in FLASH memory",
+            "name [value]",
+            do_alias
+    );
+
+static void
+make_alias(char *alias, char *name)
+{
+    diag_sprintf(alias, "alias/%s", name);
+}
+
+static void
+do_alias(int argc, char *argv[])
+{
+    char name[80];
+    char *val;
+    struct config_option opt;
+
+    switch (argc) {
+    case 2:
+        make_alias(name, argv[1]);
+        if (flash_get_config(name, &val, CONFIG_STRING)) {
+            diag_printf("'%s' = '%s'\n", argv[1], val);
+        } else {
+            diag_printf("'%s' not found\n", argv[1]);
+        }
+        break;
+    case 3:
+        if (strlen(argv[2]) >= MAX_STRING_LENGTH) {
+            diag_printf("Sorry, value is too long\n");
+            break;
+        }
+        make_alias(name, argv[1]);
+        opt.type = CONFIG_STRING;
+        opt.enable = (char *)0;
+        opt.enable_sense = 1;
+        opt.key = name;
+        opt.dflt = (CYG_ADDRESS)argv[2];
+        flash_add_config(&opt, true);
+        break;
+    default:
+        diag_printf("usage: alias name [value]\n");
+    }
+}
+
+// Lookup an alias. First try plain string aliases. If that fails try
+// other types so allowing access to all configured values. This allows
+// for alias (macro) expansion of normal 'fconfig' data, such as the
+// board IP address.
+char *
+flash_lookup_alias(char *alias, char *alias_buf)
+{
+    char name[80];
+    char *val;
+    unsigned char * dp;
+    void *val_ptr;
+    int type;
+    bool hold_bool_val;
+    long hold_long_val;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    int esa_ptr;
+#endif
+
+    make_alias(name, alias);
+    if (flash_get_config(name, &val, CONFIG_STRING)) {
+        return val;
+    } else {
+        dp = flash_lookup_config(alias);
+        if (dp) {
+            val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
+            switch (type = CONFIG_OBJECT_TYPE(dp)) {
+            case CONFIG_BOOL:
+                memcpy(&hold_bool_val, val_ptr, sizeof(bool));
+                diag_sprintf(alias_buf, "%s", hold_bool_val ? "true" : "false");
+                break;
+            case CONFIG_INT:
+                memcpy(&hold_long_val, val_ptr, sizeof(unsigned long));
+                diag_sprintf(alias_buf,"%ld", hold_long_val);
+                break;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+            case CONFIG_IP:
+                diag_sprintf(alias_buf,"%s", inet_ntoa((in_addr_t *)val_ptr));
+                break;
+            case CONFIG_ESA:
+                for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
+                    diag_sprintf(alias_buf+(3*esa_ptr), "0x%02X", ((unsigned char *)val_ptr)[esa_ptr]);
+                    if (esa_ptr < (sizeof(enet_addr_t)-1)) diag_printf(":");
+                }
+                break;
+#endif
+            case CONFIG_SCRIPT:
+                return (char *) val_ptr;
+                break;
+            default:
+                return (char *)NULL;
+            }
+            return alias_buf;
+        } 
+        return (char *)NULL;
+    }
+}
+
+#endif //  CYGSEM_REDBOOT_FLASH_ALIASES
+
+//
+// Write the in-memory copy of the configuration data to the flash device.
+//
+void
+flash_write_config(void)
+{
+#if defined(CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG) && defined(CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH)
+    int stat;
+    void *err_addr;
+#endif
+
+    config->len = sizeof(struct _config);
+    config->key1 = CONFIG_KEY1;  
+    config->key2 = CONFIG_KEY2;
+    config->cksum = cyg_crc32((unsigned char *)config, sizeof(struct _config)-sizeof(config->cksum));
+    if (verify_action("Update RedBoot non-volatile configuration")) {
+#ifdef CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH
+#ifdef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
+        memcpy(fis_work_block, fis_addr, fisdir_size);
+        fis_update_directory();
+#else //  CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
+#ifdef CYGSEM_REDBOOT_FLASH_LOCK_SPECIAL
+        // Insure [quietly] that the config page is unlocked before trying to update
+        flash_unlock((void *)cfg_base, cfg_size, (void **)&err_addr);
+#endif
+        if ((stat = flash_erase(cfg_base, cfg_size, (void **)&err_addr)) != 0) {
+            diag_printf("   initialization failed at %p: %s\n", err_addr, flash_errmsg(stat));
+        } else {
+            if ((stat = flash_program(cfg_base, (void *)config, sizeof(struct _config), 
+                                      (void **)&err_addr)) != 0) {
+                diag_printf("Error writing config data at %p: %s\n", 
+                            err_addr, flash_errmsg(stat));
+            }
+        }
+#ifdef CYGSEM_REDBOOT_FLASH_LOCK_SPECIAL
+        // Insure [quietly] that the config data is locked after the update
+        flash_lock((void *)cfg_base, cfg_size, (void **)&err_addr);
+#endif
+#endif
+#else
+        write_eeprom(config, sizeof(struct _config));  // into 'config'
+#endif
+    }
+}
+
+//
+// Find the configuration entry for a particular key
+//
+static unsigned char *
+flash_lookup_config(char *key)
+{
+    unsigned char *dp;
+    int len;
+
+    if (!config_ok) return (unsigned char *)NULL;
+
+    dp = &config->config_data[0];
+    while (dp < &config->config_data[sizeof(config->config_data)]) {
+        len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) +
+            config_length(CONFIG_OBJECT_TYPE(dp));
+        if (strcmp(key, CONFIG_OBJECT_KEY(dp)) == 0) {
+            return dp;
+        }
+        dp += len;
+    }
+//    diag_printf("Can't find config data for '%s'\n", key);
+    return false;
+}
+
+//
+// Retrieve a data object from the data base (in memory copy)
+//
+bool
+flash_get_config(char *key, void *val, int type)
+{
+    unsigned char *dp;
+    void *val_ptr;
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
+    struct _config *save_config = 0;
+#endif
+
+    if (!config_ok) return false;
+
+    if ((dp = flash_lookup_config(key)) != (unsigned char *)NULL) {
+        if (CONFIG_OBJECT_TYPE(dp) == type) {
+            val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
+            switch (type) {
+                // Note: the data may be unaligned in the configuration data
+            case CONFIG_BOOL:
+                memcpy(val, val_ptr, sizeof(bool));
+                break;
+            case CONFIG_INT:
+                memcpy(val, val_ptr, sizeof(unsigned long));
+                break;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+            case CONFIG_IP:
+                memcpy(val, val_ptr, sizeof(in_addr_t));
+                break;
+            case CONFIG_ESA:
+                memcpy(val, val_ptr, sizeof(enet_addr_t));
+                break;
+#endif
+#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
+	    case CONFIG_NETPORT:
+#endif
+            case CONFIG_STRING:
+            case CONFIG_SCRIPT:
+                // Just return a pointer to the script/line
+                *(unsigned char **)val = (unsigned char *)val_ptr;
+                break;
+            }
+        } else {
+            diag_printf("Request for config value '%s' - wrong type\n", key);
+        }
+        return true;
+    }
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
+    // Did not find key. Is configuration data valid?
+    // Check to see if the config data is valid, if not, revert to 
+    // readonly mode, by setting config to readonly_config.  We
+    // will set it back before we leave this function.
+    if ( (config != readonly_config) && ((cyg_crc32((unsigned char *)config, 
+               sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
+        (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2))) {
+        save_config = config;
+        config = readonly_config;
+        if ((cyg_crc32((unsigned char *)config, 
+                       sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
+            (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2)) {
+            diag_printf("FLASH configuration checksum error or invalid key\n");
+            config = save_config;
+            return false;
+        }
+        else{
+            diag_printf("Getting config information in READONLY mode\n");
+            return flash_get_config(key, val, type);
+        }        
+    }
+#endif
+    return false;
+}
+
+//
+// Copy data into the config area
+//
+static void
+flash_config_insert_value(unsigned char *dp, struct config_option *opt)
+{
+    switch (opt->type) {
+        // Note: the data may be unaligned in the configuration data
+    case CONFIG_BOOL:
+        memcpy(dp, (void *)&opt->dflt, sizeof(bool));
+        break;
+    case CONFIG_INT:
+        memcpy(dp, (void *)&opt->dflt, sizeof(unsigned long));
+        break;
+#ifdef CYGPKG_REDBOOT_NETWORKING
+    case CONFIG_IP:
+        memcpy(dp, (void *)&opt->dflt, sizeof(in_addr_t));
+        break;
+    case CONFIG_ESA:
+        memcpy(dp, (void *)opt->dflt, sizeof(enet_addr_t));
+        break;
+#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
+    case CONFIG_NETPORT:
+	// validate dflt and if not acceptable use first port
+        {
+	    int index;
+	    const char *name;
+	    for (index = 0; (name = net_devname(index)) != NULL; index++)
+		if (!strcmp((char *)opt->dflt, name))
+		    break;
+	    if (name == NULL)
+		name = net_devname(0);
+	    memcpy(dp, name, strlen(name) + 1);
+        }
+        break;
+#endif
+#endif
+    case CONFIG_STRING:
+        memcpy(dp, (void *)opt->dflt, config_length(CONFIG_STRING));
+        break;
+    case CONFIG_SCRIPT:
+        break;
+    }
+}
+
+//
+// Add a new option to the database
+//
+bool
+flash_add_config(struct config_option *opt, bool update)
+{
+    unsigned char *dp, *kp;
+    int len, elen, size;
+
+    // If data item is already present, just update it
+    // Note: only the data value can be thusly changed
+    if ((dp = flash_lookup_config(opt->key)) != (unsigned char *)NULL) {
+        flash_config_insert_value(CONFIG_OBJECT_VALUE(dp), opt);
+        if (update) {
+            flash_write_config();
+        }
+        return true;
+    }
+    // Add the data item
+    dp = &config->config_data[0];
+    size = 0;
+    while (size < sizeof(config->config_data)) {
+        if (CONFIG_OBJECT_TYPE(dp) == CONFIG_EMPTY) {
+            kp = opt->key;
+            len = strlen(kp) + 1;
+            size += len + 2 + 2 + config_length(opt->type);
+            if (opt->enable) {
+                elen = strlen(opt->enable) + 1;
+                size += elen;
+            } else {
+                elen = 0;
+            }
+            if (size > sizeof(config->config_data)) {
+                break;
+            }
+            CONFIG_OBJECT_TYPE(dp) = opt->type; 
+            CONFIG_OBJECT_KEYLEN(dp) = len;
+            CONFIG_OBJECT_ENABLE_SENSE(dp) = opt->enable_sense;
+            CONFIG_OBJECT_ENABLE_KEYLEN(dp) = elen;
+            dp = CONFIG_OBJECT_KEY(dp);
+            while (*kp) *dp++ += *kp++;
+            *dp++ = '\0';    
+            if (elen) {
+                kp = opt->enable;
+                while (*kp) *dp++ += *kp++;
+                *dp++ = '\0';    
+            }
+            flash_config_insert_value(dp, opt);
+            if (update) {
+                flash_write_config();
+            }
+            return true;
+        } else {
+            len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) +
+                config_length(CONFIG_OBJECT_TYPE(dp));
+            dp += len;
+            size += len;
+        }
+    }
+    diag_printf("No space to add '%s'\n", opt->key);
+    return false;
+}
+
+//
+// Reset/initialize configuration data - used only when starting from scratch
+//
+static void
+config_init(void)
+{
+    // Well known option strings
+    struct config_option *optend = __CONFIG_options_TAB_END__;
+    struct config_option *opt = __CONFIG_options_TAB__;
+
+    memset(config, 0, sizeof(struct _config));
+    while (opt != optend) {
+        if (!flash_add_config(opt, false)) {
+            return;
+        }
+        opt++;
+    }
+    config_ok = true;
+}
+
+//
+// Attempt to get configuration information from the FLASH.
+// If available (i.e. good checksum, etc), initialize "known"
+// values for later use.
+//
+static void
+load_flash_config(void)
+{
+    bool use_boot_script;
+    void *err_addr;
+    unsigned char *cfg_temp = (unsigned char *)workspace_end;
+
+    config_ok = false;
+    script = (unsigned char *)0;
+    cfg_temp -= sizeof(struct _config);  // Space for primary config data
+    config = (struct _config *)cfg_temp;
+    cfg_temp -= sizeof(struct _config);  // Space for backup config data
+    backup_config = (struct _config *)cfg_temp;
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
+    cfg_temp -= sizeof(struct _config);  // Space for readonly copy of config data
+    readonly_config = (struct _config *)cfg_temp;
+#endif
+    workspace_end = cfg_temp;
+#ifdef CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH
+    if (!do_flash_init()) return;
+    cfg_size = (flash_block_size > sizeof(struct _config)) ? 
+        sizeof(struct _config) : 
+        _rup(sizeof(struct _config), flash_block_size);
+#ifdef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
+    cfg_size = _rup(cfg_size, sizeof(struct fis_image_desc));
+    if ((flash_block_size-cfg_size) < 8*sizeof(struct fis_image_desc)) {
+        // Too bad this can't be checked at compile/build time
+        diag_printf("Sorry, FLASH config exceeds available space in FIS directory\n");
+        return;
+    }
+    fisdir_size = flash_block_size - cfg_size;
+    cfg_base = (void *)(((CYG_ADDRESS)fis_addr + flash_block_size) - cfg_size);
+#else
+    if (CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK < 0) {
+        cfg_base = (void *)((CYG_ADDRESS)flash_end + 1 -
+           _rup(_rup((-CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK*flash_block_size), cfg_size), flash_block_size));
+    } else {
+        cfg_base = (void *)((CYG_ADDRESS)flash_start + 
+           _rup(_rup((CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK*flash_block_size), cfg_size), flash_block_size));
+    }
+#endif
+    flash_read((void *)cfg_base, (void *)config, sizeof(struct _config), (void **)&err_addr);
+#else
+    read_eeprom(config, sizeof(struct _config));  // into 'config'
+#endif
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
+    memcpy(readonly_config, config, sizeof(struct _config));
+#endif
+    if ((cyg_crc32((unsigned char *)config, 
+                   sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
+        (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2)) {
+        diag_printf("FLASH configuration checksum error or invalid key\n");
+        config_init();
+        return;
+    }
+    config_ok = true;
+    flash_get_config("boot_script", &use_boot_script, CONFIG_BOOL);
+    if (use_boot_script) {
+        flash_get_config("boot_script_data", &script, CONFIG_SCRIPT);
+        flash_get_config("boot_script_timeout", &script_timeout, CONFIG_INT);
+    }
+#ifdef CYGSEM_REDBOOT_VARIABLE_BAUD_RATE
+    if (flash_get_config("console_baud_rate", &console_baud_rate, CONFIG_INT)) {
+        extern int set_console_baud_rate(int);
+        set_console_baud_rate(console_baud_rate);
+    }
+#endif
+}
+
+RedBoot_init(load_flash_config, RedBoot_INIT_FIRST);
+
+// EOF fconfig.c
--- a/packages/redboot/current/src/flash.c
+++ b/packages/redboot/current/src/flash.c
@@ -9,6 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003 Red Hat, Inc.
+// Copyright (C) 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -64,23 +65,6 @@
 // Round a quantity up
 #define _rup(n,s) ((((n)+(s-1))/s)*s)
 
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
-#include <flash_config.h>
-
-// Configuration data, saved in FLASH, used to set/update RedBoot
-// normal "configuration" data items.
-static struct _config {
-    unsigned long len;
-    unsigned long key1;
-    unsigned char config_data[MAX_CONFIG_DATA-(4*4)];
-    unsigned long key2;
-    unsigned long cksum;
-} *config, *backup_config;
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
-static struct _config  *readonly_config;
-#endif
-#endif
-
 #ifdef CYGOPT_REDBOOT_FIS
 // Image management functions
 local_cmd_entry("init",
@@ -178,18 +162,17 @@ RedBoot_nested_cmd("fis",
     );
 
 // Local data used by these routines
-static void *flash_start, *flash_end;
-static int flash_block_size, flash_num_blocks;
+void *flash_start, *flash_end;
+int flash_block_size, flash_num_blocks;
 #ifdef CYGOPT_REDBOOT_FIS
-static void *fis_work_block;
-static void *fis_addr;
-static int fisdir_size;  // Size of FIS directory.
+void *fis_work_block;
+void *fis_addr;
+int fisdir_size;  // Size of FIS directory.
 #endif
 #ifdef CYGSEM_REDBOOT_FLASH_CONFIG
-static void *cfg_base;   // Location in Flash of config data
-static int   cfg_size;   // Length of config data - rounded to Flash block size
-// Prototypes for local functions
-static unsigned char *flash_lookup_config(char *key);
+extern void *cfg_base;   // Location in Flash of config data
+extern int   cfg_size;   // Length of config data - rounded to Flash block size
+extern struct _config *config;
 #endif
 
 static void
@@ -212,7 +195,9 @@ fis_lookup(char *name, int *num)
 {
     int i;
     struct fis_image_desc *img;
+    void *err_addr;
 
+    flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
     img = (struct fis_image_desc *)fis_work_block;
     for (i = 0;  i < fisdir_size/sizeof(*img);  i++, img++) {
         if ((img->name[0] != (unsigned char)0xFF) && 
@@ -224,7 +209,7 @@ fis_lookup(char *name, int *num)
     return (struct fis_image_desc *)0;
 }
 
-static void
+void
 fis_update_directory(void)
 {
     int stat;
@@ -324,7 +309,7 @@ fis_init(int argc, char *argv[])
     img++;
     redboot_flash_start += redboot_image_size;
 #endif
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
+#if defined(CYGSEM_REDBOOT_FLASH_CONFIG) && defined(CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH)
     // And a descriptor for the configuration data
     memset(img, 0, sizeof(*img));
     strcpy(img->name, "RedBoot config");
@@ -402,7 +387,9 @@ fis_init(int argc, char *argv[])
         erase_start = redboot_flash_start; // high water of created images
         // Now the empty bits between the end of Redboot and the cfg and dir 
         // blocks. 
-#if defined(CYGSEM_REDBOOT_FLASH_CONFIG) && !defined(CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG)
+#if defined(CYGSEM_REDBOOT_FLASH_CONFIG) && \
+    defined(CYGHWR_REDBOOT_FLASH_CONFIG_MEDIA_FLASH) && \
+    !defined(CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG)
         if (fis_addr > cfg_base) {
           erase_size = (CYG_ADDRESS)cfg_base - erase_start; // the gap between HWM and config data
         } else {
@@ -456,6 +443,7 @@ fis_list(int argc, char *argv[])
     bool show_cksums = false;
     bool show_datalen = false;
     struct option_info opts[2];
+    void *err_addr;
 
 #ifdef CYGHWR_REDBOOT_ARM_FLASH_SIB
     // FIXME: this is somewhat half-baked
@@ -477,7 +465,8 @@ fis_list(int argc, char *argv[])
     {
         return;
     }
-    img = (struct fis_image_desc *) fis_addr;
+    flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
+    img = (struct fis_image_desc *) fis_work_block;
     // Let diag_printf do the formatting in both cases, rather than counting
     // cols by hand....
     diag_printf("%-16s  %-10s  %-10s  %-10s  %-s\n",
@@ -506,9 +495,11 @@ fis_free(int argc, char *argv[])
 {
     unsigned long *fis_ptr, *fis_end;
     unsigned long *area_start;
+    void *err_addr;
 
     // Do not search the area reserved for pre-RedBoot systems:
-    fis_ptr = (unsigned long *)((CYG_ADDRESS)flash_start + 
+    flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
+    fis_ptr = (unsigned long *)((CYG_ADDRESS)fis_work_block + 
                                 CYGNUM_REDBOOT_FLASH_RESERVED_BASE + 
                                 CYGBLD_REDBOOT_MIN_IMAGE_SIZE);
     fis_end = (unsigned long *)(CYG_ADDRESS)flash_end;
@@ -545,9 +536,11 @@ fis_find_free(CYG_ADDRESS *addr, unsigne
 {
     unsigned long *fis_ptr, *fis_end;
     unsigned long *area_start;
+    void *err_addr;
 
     // Do not search the area reserved for pre-RedBoot systems:
-    fis_ptr = (unsigned long *)((CYG_ADDRESS)flash_start + 
+    flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
+    fis_ptr = (unsigned long *)((CYG_ADDRESS)fis_work_block + 
                                 CYGNUM_REDBOOT_FLASH_RESERVED_BASE + 
                                 CYGBLD_REDBOOT_MIN_IMAGE_SIZE);
     fis_end = (unsigned long *)(CYG_ADDRESS)flash_end;
@@ -623,7 +616,7 @@ fis_create(int argc, char *argv[])
         return;
     }
 
-    memcpy(fis_work_block, fis_addr, fisdir_size);
+    flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
     defaults_assumed = false;
     if (name) {
         // Search existing files to acquire defaults for params not specified:
@@ -779,7 +772,12 @@ fis_create(int argc, char *argv[])
         img->size = length;
         img->data_length = img_size;
 #ifdef CYGSEM_REDBOOT_FIS_CRC_CHECK
-        img->file_cksum = cyg_crc32((unsigned char *)flash_addr, img_size);
+        if (!no_copy) {
+            img->file_cksum = cyg_crc32((unsigned char *)mem_addr, img_size);
+        } else {
+            // No way to compute this, sorry
+            img->file_cksum = 0;
+        }
 #endif
         fis_update_directory();
     }
@@ -825,7 +823,6 @@ fis_delete(int argc, char *argv[])
     num_reserved++;
 #endif
 
-    memcpy(fis_work_block, fis_addr, fisdir_size);
     img = fis_lookup(name, &i);
     if (img) {
         if (i < num_reserved) {
@@ -864,6 +861,7 @@ fis_load(int argc, char *argv[])
 #ifdef CYGPKG_COMPRESS_ZLIB
     bool decompress = false;
 #endif
+    void *err_addr;
 
     init_opts(&opts[0], 'b', true, OPTION_ARG_TYPE_NUM, 
               (void **)&mem_addr, (bool *)&mem_addr_set, "memory [load] base address");
@@ -881,7 +879,6 @@ fis_load(int argc, char *argv[])
         fis_usage("invalid arguments");
         return;
     }
-    memcpy(fis_work_block, fis_addr, fisdir_size);
     if ((img = fis_lookup(name, NULL)) == (struct fis_image_desc *)0) {
         diag_printf("No image '%s' found\n", name);
         return;
@@ -891,9 +888,8 @@ fis_load(int argc, char *argv[])
     }
     // Load image from FLASH into RAM
 #ifdef CYGSEM_REDBOOT_VALIDATE_USER_RAM_LOADS
-    if ((mem_addr < (CYG_ADDRESS)user_ram_start) ||
-        ((mem_addr+img->data_length) >= (CYG_ADDRESS)user_ram_end)) {
-        diag_printf("Not a loadable image\n");
+    if (!valid_address((void *)mem_addr)) {
+        diag_printf("Not a loadable image - try using -b ADDRESS option\n");
         return;
     }
 #endif
@@ -927,11 +923,11 @@ fis_load(int argc, char *argv[])
         load_address_end = (unsigned long)p->out_buf;
 
     	// Reload fis directory
-	memcpy(fis_work_block, fis_addr, fisdir_size);
+        flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
     } else // dangling block
 #endif
     {
-        memcpy((void *)mem_addr, (void *)img->flash_base, img->data_length);
+        flash_read((void *)img->flash_base, (void *)mem_addr, img->data_length, (void **)&err_addr);
 
         // Set load address/top
         load_address = mem_addr;
@@ -949,6 +945,7 @@ fis_load(int argc, char *argv[])
         if (cksum != img->file_cksum) {
             diag_printf("** Warning - checksum failure.  stored: 0x%08lx, computed: 0x%08lx\n",
                         img->file_cksum, cksum);
+            entry_address = NO_MEMORY;
         }
     }
 #endif
@@ -1105,7 +1102,6 @@ fis_lock(int argc, char *argv[])
     /* Get parameters from image if specified */
     if (name) {
         struct fis_image_desc *img;
-	memcpy(fis_work_block, fis_addr, fisdir_size);
         if ((img = fis_lookup(name, NULL)) == (struct fis_image_desc *)0) {
             diag_printf("No image '%s' found\n", name);
             return;
@@ -1152,7 +1148,6 @@ fis_unlock(int argc, char *argv[])
 
     if (name) {
         struct fis_image_desc *img;
-	memcpy(fis_work_block, fis_addr, fisdir_size);
         if ((img = fis_lookup(name, NULL)) == (struct fis_image_desc *)0) {
             diag_printf("No image '%s' found\n", name);
             return;
@@ -1178,7 +1173,7 @@ fis_unlock(int argc, char *argv[])
 #endif
 
 // This is set non-zero if the FLASH subsystem has successfully been initialized
-static int __flash_init = 0;
+int __flash_init = 0;
 
 void
 _flash_info(void)
@@ -1188,10 +1183,11 @@ void
            flash_start, (CYG_ADDRWORD)flash_end + 1, flash_num_blocks, (void *)flash_block_size);
 }
 
-static bool
+bool
 do_flash_init(void)
 {
     int stat;
+    void *err_addr;
 
     if (!__flash_init) {
         if ((stat = flash_init((void *)(workspace_end-FLASH_MIN_WORKSPACE), 
@@ -1224,7 +1220,7 @@ do_flash_init(void)
             fis_addr = (void *)((CYG_ADDRESS)flash_start + 
                                 (CYGNUM_REDBOOT_FIS_DIRECTORY_BLOCK*flash_block_size));
         }
-		memcpy(fis_work_block, fis_addr, flash_block_size);
+        flash_read(fis_addr, fis_work_block, fisdir_size, (void **)&err_addr);
 #endif
         __flash_init = 1;
     }
@@ -1263,907 +1259,4 @@ do_fis(int argc, char *argv[])
     fis_usage("unrecognized command");
 }
 
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
-
-static bool config_ok;
-
-#define CONFIG_KEY1    0x0BADFACE
-#define CONFIG_KEY2    0xDEADDEAD
-
-#define CONFIG_DONE    0
-#define CONFIG_ABORT  -1
-#define CONFIG_CHANGED 1
-#define CONFIG_OK      2
-#define CONFIG_BACK    3
-#define CONFIG_BAD     4
-
-// Note: the following options are related.  If 'boot_script' is false, then
-// the other values are used in the configuration.  Because of the way
-// that configuration tables are generated, they should have names which
-// are related.  The configuration options will show up lexicographically
-// ordered, thus the peculiar naming.
-RedBoot_config_option("Run script at boot",
-                      boot_script,
-                      ALWAYS_ENABLED, true,
-                      CONFIG_BOOL,
-                      false
-    );
-RedBoot_config_option("Boot script",
-                      boot_script_data,
-                      "boot_script", true,
-                      CONFIG_SCRIPT,
-                      ""
-    );
-// Some preprocessor magic for building the [constant] prompt string
-#define __cat(s1,c2,s3) s1 #c2 s3
-#define _cat(s1,c2,s3) __cat(s1,c2,s3)
-RedBoot_config_option(_cat("Boot script timeout (",
-                           CYGNUM_REDBOOT_BOOT_SCRIPT_TIMEOUT_RESOLUTION,
-                           "ms resolution)"),
-                      boot_script_timeout,
-                      "boot_script", true,
-                      CONFIG_INT,
-                      0
-    );
-#undef __cat
-#undef _cat
-
-#ifdef CYGSEM_REDBOOT_VARIABLE_BAUD_RATE
-RedBoot_config_option("Console baud rate",
-                      console_baud_rate,
-                      ALWAYS_ENABLED, true,
-                      CONFIG_INT,
-                      CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD
-    );
-#endif
-
-CYG_HAL_TABLE_BEGIN( __CONFIG_options_TAB__, RedBoot_config_options);
-CYG_HAL_TABLE_END( __CONFIG_options_TAB_END__, RedBoot_config_options);
-
-extern struct config_option __CONFIG_options_TAB__[], __CONFIG_options_TAB_END__[];
-
-// 
-// Layout of config data
-// Each data item is variable length, with the name, type and dependencies
-// encoded into the object.
-//  offset   contents
-//       0   data type
-//       1   length of name (N)
-//       2   enable sense
-//       3   length of enable key (M)
-//       4   key name
-//     N+4   enable key
-//   M+N+4   data value
-//
-
-#define CONFIG_OBJECT_TYPE(dp)          (dp)[0]
-#define CONFIG_OBJECT_KEYLEN(dp)        (dp)[1]
-#define CONFIG_OBJECT_ENABLE_SENSE(dp)  (dp)[2]
-#define CONFIG_OBJECT_ENABLE_KEYLEN(dp) (dp)[3]
-#define CONFIG_OBJECT_KEY(dp)           ((dp)+4)
-#define CONFIG_OBJECT_ENABLE_KEY(dp)    ((dp)+4+CONFIG_OBJECT_KEYLEN(dp))
-#define CONFIG_OBJECT_VALUE(dp)         ((dp)+4+CONFIG_OBJECT_KEYLEN(dp)+CONFIG_OBJECT_ENABLE_KEYLEN(dp))
-
-#define LIST_OPT_LIST_ONLY (1)
-#define LIST_OPT_NICKNAMES (2)
-#define LIST_OPT_FULLNAMES (4)
-#define LIST_OPT_DUMBTERM  (8)
-
-static void config_init(void);
-
-static int
-get_config(unsigned char *dp, char *title, int list_opt, char *newvalue )
-{
-    char line[256], hold_line[256], *sp, *lp;
-    int ret;
-    bool hold_bool_val, new_bool_val, enable;
-    unsigned long hold_int_val, new_int_val;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    in_addr_t hold_ip_val, new_ip_val;
-    enet_addr_t hold_esa_val;
-    int esa_ptr;
-    char *esp;
-#endif
-    void *val_ptr;
-    int type;
-
-    if (CONFIG_OBJECT_ENABLE_KEYLEN(dp)) {
-        flash_get_config(CONFIG_OBJECT_ENABLE_KEY(dp), &enable, CONFIG_BOOL);
-        if (((bool)CONFIG_OBJECT_ENABLE_SENSE(dp) && !enable) ||
-            (!(bool)CONFIG_OBJECT_ENABLE_SENSE(dp) && enable)) {
-            return CONFIG_OK;  // Disabled field
-        }
-    }
-    lp = line;  *lp = '\0';
-    val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
-    if (LIST_OPT_NICKNAMES & list_opt)
-        diag_printf("%s: ", CONFIG_OBJECT_KEY(dp));
-    if (LIST_OPT_FULLNAMES & list_opt) {
-        if (title != (char *)NULL) {
-            diag_printf("%s: ", title);
-        } else {
-            diag_printf("%s: ", CONFIG_OBJECT_KEY(dp));
-        }
-    }
-    switch (type = CONFIG_OBJECT_TYPE(dp)) {
-    case CONFIG_BOOL:
-        memcpy(&hold_bool_val, val_ptr, sizeof(bool));
-        lp += diag_sprintf(lp, "%s", hold_bool_val ? "true" : "false");
-        break;
-    case CONFIG_INT:
-        memcpy(&hold_int_val, val_ptr, sizeof(unsigned long));
-        lp += diag_sprintf(lp, "%ld", hold_int_val);
-        break;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    case CONFIG_IP:
-        lp += diag_sprintf(lp, "%s", inet_ntoa((in_addr_t *)val_ptr));
-        if (0 == strcmp("0.0.0.0", line) && !(LIST_OPT_LIST_ONLY & list_opt)) {
-            // then we have a deeply unhelpful starting text - kill it off
-            // (unless we are just listing all values)
-            lp = line;  *lp = '\0';
-        }
-        break;
-    case CONFIG_ESA:
-        for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
-            lp += diag_sprintf(lp, "0x%02X", ((unsigned char *)val_ptr)[esa_ptr]);
-            if (esa_ptr < (sizeof(enet_addr_t)-1)) lp += diag_sprintf(lp, ":");
-        }
-        break;
-#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
-    case CONFIG_NETPORT:
-        lp += diag_sprintf(lp, "%s", (unsigned char *)val_ptr);
-        break;
-#endif
-#endif
-    case CONFIG_STRING:
-        lp += diag_sprintf(lp, "%s", (unsigned char *)val_ptr);
-        break;
-    case CONFIG_SCRIPT:
-        diag_printf("\n");
-        sp = lp = (unsigned char *)val_ptr;
-        while (*sp) {
-            while (*lp != '\n') lp++;
-            *lp = '\0';
-            diag_printf(".. %s\n", sp);
-            *lp++ = '\n';
-            sp = lp;
-        }
-        break;
-    }
-    if (LIST_OPT_LIST_ONLY & list_opt) {
-        diag_printf("%s\n", line);
-        return CONFIG_OK;
-    }
-    if (type != CONFIG_SCRIPT) {
-        if (NULL != newvalue) {
-            ret = strlen(newvalue);
-            if (ret > sizeof(line))
-                return CONFIG_BAD;
-            strcpy(hold_line, line); // Hold the old value for comparison
-            strcpy(line, newvalue);
-            diag_printf("Setting to %s\n", newvalue);
-        } else {
-            // read from terminal
-            strcpy(hold_line, line);
-            if (LIST_OPT_DUMBTERM & list_opt) {
-                diag_printf( (CONFIG_STRING == type ?
-                              "%s > " :
-                              "%s ? " ), line);
-                *line = '\0';
-            }
-            ret = _rb_gets_preloaded(line, sizeof(line), 0);
-        }
-        if (ret < 0) return CONFIG_ABORT;
-        // empty input - leave value untouched (else DNS goes away for a
-        // minute to try to look it up) but we must accept empty value for strings.
-        if (0 == line[0] && CONFIG_STRING != type) return CONFIG_OK; 
-        if (strcmp(line, hold_line) == 0) return CONFIG_OK;  // Just a CR - leave value untouched
-        lp = &line[strlen(line)-1];
-        if (*lp == '.') return CONFIG_DONE;
-        if (*lp == '^') return CONFIG_BACK;
-    }
-    switch (type) {
-    case CONFIG_BOOL:
-        memcpy(&hold_bool_val, val_ptr, sizeof(bool));
-        if (!parse_bool(line, &new_bool_val)) {
-            return CONFIG_BAD;
-        }
-        if (hold_bool_val != new_bool_val) {
-            memcpy(val_ptr, &new_bool_val, sizeof(bool));
-            return CONFIG_CHANGED;
-        } else {
-            return CONFIG_OK;
-        }
-        break;
-    case CONFIG_INT:
-        memcpy(&hold_int_val, val_ptr, sizeof(unsigned long));
-        if (!parse_num(line, &new_int_val, 0, 0)) {
-            return CONFIG_BAD;
-        }
-        if (hold_int_val != new_int_val) {
-            memcpy(val_ptr, &new_int_val, sizeof(unsigned long));
-            return CONFIG_CHANGED;
-        } else {
-            return CONFIG_OK;
-        }
-        break;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    case CONFIG_IP:
-        memcpy(&hold_ip_val.s_addr, &((in_addr_t *)val_ptr)->s_addr, sizeof(in_addr_t));
-        if (!_gethostbyname(line, &new_ip_val)) {
-            return CONFIG_BAD;
-        }
-        if (hold_ip_val.s_addr != new_ip_val.s_addr) {
-            memcpy(val_ptr, &new_ip_val, sizeof(in_addr_t));
-            return CONFIG_CHANGED;
-        } else {
-            return CONFIG_OK;
-        }
-        break;
-    case CONFIG_ESA:
-        memcpy(&hold_esa_val, val_ptr, sizeof(enet_addr_t));
-        esp = line;
-        for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
-            unsigned long esa_byte;
-            if (!parse_num(esp, &esa_byte, &esp, ":")) {
-                memcpy(val_ptr, &hold_esa_val, sizeof(enet_addr_t));
-                return CONFIG_BAD;
-            }
-            ((unsigned char *)val_ptr)[esa_ptr] = esa_byte;
-        }
-        return CONFIG_CHANGED;
-        break;
-#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
-    case CONFIG_NETPORT:
-	if (strlen(line) >= MAX_STRING_LENGTH || net_devindex(line) < 0) {
-	    int index;
-	    const char *name;
-	    diag_printf("Sorry, Port name must be one of:\n");
-	    for (index = 0; (name = net_devname(index)) != NULL; index++)
-		diag_printf("    %s\n", name);
-            return CONFIG_BAD;
-	}
-        strcpy((unsigned char *)val_ptr, line);
-	break;
-#endif
-#endif
-    case CONFIG_SCRIPT:
-        // Assume it always changes
-        sp = (unsigned char *)val_ptr;
-        diag_printf("Enter script, terminate with empty line\n");
-        while (true) {
-            *sp = '\0';
-            diag_printf(">> ");
-            ret = _rb_gets(line, sizeof(line), 0);
-            if (ret < 0) return CONFIG_ABORT;
-            if (strlen(line) == 0) break;
-            lp = line;
-            while (*lp) {
-                *sp++ = *lp++;
-            }
-            *sp++ = '\n';
-        }
-        break;
-    case CONFIG_STRING:
-        if (strlen(line) >= MAX_STRING_LENGTH) {
-            diag_printf("Sorry, value is too long\n");
-            return CONFIG_BAD;
-        }
-        strcpy((unsigned char *)val_ptr, line);
-        break;
-    }
-    return CONFIG_CHANGED;
-}
-
-//
-// Manage configuration information with the FLASH
-//
-
-static int
-config_length(int type)
-{
-    switch (type) {
-    case CONFIG_BOOL:
-        return sizeof(bool);
-    case CONFIG_INT:
-        return sizeof(unsigned long);
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    case CONFIG_IP:
-        return sizeof(in_addr_t);
-    case CONFIG_ESA:
-        // Would like this to be sizeof(enet_addr_t), but that causes much
-        // pain since it fouls the alignment of data which follows.
-        return 8;
-#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
-    case CONFIG_NETPORT:
-        return MAX_STRING_LENGTH;
-#endif
-#endif
-    case CONFIG_STRING:
-        return MAX_STRING_LENGTH;
-    case CONFIG_SCRIPT:
-        return MAX_SCRIPT_LENGTH;
-    default:
-        return 0;
-    }
-}
-
-static cmd_fun do_flash_config;
-RedBoot_cmd("fconfig",
-            "Manage configuration kept in FLASH memory",
-            "[-i] [-l] [-n] [-f] [-d] | [-d] nickname [value]",
-            do_flash_config
-    );
-
-static void
-do_flash_config(int argc, char *argv[])
-{
-    bool need_update = false;
-    struct config_option *optend = __CONFIG_options_TAB_END__;
-    struct config_option *opt = __CONFIG_options_TAB__;
-    struct option_info opts[5];
-    bool list_only;
-    bool nicknames;
-    bool fullnames;
-    bool dumbterminal;
-    int list_opt = 0;
-    unsigned char *dp;
-    int len, ret;
-    char *title;
-    char *onlyone = NULL;
-    char *onevalue = NULL;
-    bool doneone = false;
-    bool init = false;
-
-    if (!__flash_init) {
-        diag_printf("Sorry, no FLASH memory is available\n");
-        return;
-    }
-    memcpy(backup_config, config, sizeof(struct _config));
-    script = (unsigned char *)0;
-
-    init_opts(&opts[0], 'l', false, OPTION_ARG_TYPE_FLG, 
-              (void **)&list_only, (bool *)0, "list configuration only");
-    init_opts(&opts[1], 'n', false, OPTION_ARG_TYPE_FLG, 
-              (void **)&nicknames, (bool *)0, "show nicknames");
-    init_opts(&opts[2], 'f', false, OPTION_ARG_TYPE_FLG, 
-              (void **)&fullnames, (bool *)0, "show full names");
-    init_opts(&opts[3], 'i', false, OPTION_ARG_TYPE_FLG, 
-              (void **)&init, (bool *)0, "initialize configuration database");
-    init_opts(&opts[4], 'd', false, OPTION_ARG_TYPE_FLG, 
-              (void **)&dumbterminal, (bool *)0, "dumb terminal: no clever edits");
-
-    // First look to see if we are setting or getting a single option
-    // by just quoting its nickname
-    if ( (2 == argc && '-' != argv[1][0]) ||
-         (3 == argc && '-' != argv[1][0] && '-' != argv[2][0])) {
-        // then the command was "fconfig foo [value]"
-        onlyone = argv[1];
-        onevalue = (3 == argc) ? argv[2] : NULL;
-        list_opt = LIST_OPT_NICKNAMES;
-    }
-    // Next see if we are setting or getting a single option with a dumb
-    // terminal invoked, ie. no line editing.
-    else if (3 == argc &&
-             '-' == argv[1][0] && 'd' == argv[1][1] && 0 == argv[1][2] && 
-             '-' != argv[2][0]) {
-        // then the command was "fconfig -d foo"
-        onlyone = argv[2];
-        onevalue = NULL;
-        list_opt = LIST_OPT_NICKNAMES | LIST_OPT_DUMBTERM;
-    }
-    else {
-        if (!scan_opts(argc, argv, 1, opts, 5, 0, 0, ""))
-            return;
-        list_opt |= list_only ? LIST_OPT_LIST_ONLY : 0;
-        list_opt |= nicknames ? LIST_OPT_NICKNAMES : LIST_OPT_FULLNAMES;
-        list_opt |= fullnames ? LIST_OPT_FULLNAMES : 0;
-        list_opt |= dumbterminal ? LIST_OPT_DUMBTERM : 0;
-    }
-
-    if (init && verify_action("Initialize non-volatile configuration")) {
-        config_init();
-        need_update = true;
-    }
-
-    dp = &config->config_data[0];
-    while (dp < &config->config_data[sizeof(config->config_data)]) {
-        if (CONFIG_OBJECT_TYPE(dp) == CONFIG_EMPTY) {
-            break;
-        }
-        len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) + 
-            config_length(CONFIG_OBJECT_TYPE(dp));
-        // Provide a title for well known [i.e. builtin] objects
-        title = (char *)NULL;
-        opt = __CONFIG_options_TAB__;
-        while (opt != optend) {
-            if (strcmp(opt->key, CONFIG_OBJECT_KEY(dp)) == 0) {
-                title = opt->title;
-                break;
-            }
-            opt++;
-        }
-        if ( onlyone && 0 != strcmp(CONFIG_OBJECT_KEY(dp), onlyone) )
-            ret = CONFIG_OK; // skip this entry
-        else {
-            doneone = true;
-            ret = get_config(dp, title, list_opt, onevalue); // do this opt
-        }
-        switch (ret) {
-        case CONFIG_DONE:
-            goto done;
-        case CONFIG_ABORT:
-            memcpy(config, backup_config, sizeof(struct _config));
-            return;
-        case CONFIG_CHANGED:
-            need_update = true;
-        case CONFIG_OK:
-            dp += len;
-            break;
-        case CONFIG_BACK:
-            dp = &config->config_data[0];
-            continue;
-        case CONFIG_BAD:
-            // Nothing - make him do it again
-            diag_printf ("** invalid entry\n");
-            onevalue = NULL; // request a good value be typed in - or abort/whatever
-        }
-    }
-
- done:
-    if (NULL != onlyone && !doneone) {
-#ifdef CYGSEM_REDBOOT_ALLOW_DYNAMIC_FLASH_CONFIG_DATA
-        if (verify_action("** entry '%s' not found - add", onlyone)) {
-            struct config_option opt;
-            diag_printf("Trying to add value\n");
-        }
-#else
-        diag_printf("** entry '%s' not found", onlyone);
-#endif
-    }
-    if (!need_update)
-        return;
-    flash_write_config();
-}
-
-
-#ifdef CYGSEM_REDBOOT_FLASH_ALIASES
-static cmd_fun do_alias;
-RedBoot_cmd("alias",
-            "Manage aliases kept in FLASH memory",
-            "name [value]",
-            do_alias
-    );
-
-static void
-make_alias(char *alias, char *name)
-{
-    diag_sprintf(alias, "alias/%s", name);
-}
-
-static void
-do_alias(int argc, char *argv[])
-{
-    char name[80];
-    char *val;
-    struct config_option opt;
-
-    switch (argc) {
-    case 2:
-        make_alias(name, argv[1]);
-        if (flash_get_config(name, &val, CONFIG_STRING)) {
-            diag_printf("'%s' = '%s'\n", argv[1], val);
-        } else {
-            diag_printf("'%s' not found\n", argv[1]);
-        }
-        break;
-    case 3:
-        if (strlen(argv[2]) >= MAX_STRING_LENGTH) {
-            diag_printf("Sorry, value is too long\n");
-            break;
-        }
-        make_alias(name, argv[1]);
-        opt.type = CONFIG_STRING;
-        opt.enable = (char *)0;
-        opt.enable_sense = 1;
-        opt.key = name;
-        opt.dflt = (CYG_ADDRESS)argv[2];
-        flash_add_config(&opt, true);
-        break;
-    default:
-        diag_printf("usage: alias name [value]\n");
-    }
-}
-
-// Lookup an alias. First try plain string aliases. If that fails try
-// other types so allowing access to all configured values. This allows
-// for alias (macro) expansion of normal 'fconfig' data, such as the
-// board IP address.
-char *
-flash_lookup_alias(char *alias, char *alias_buf)
-{
-    char name[80];
-    char *val;
-    unsigned char * dp;
-    void *val_ptr;
-    int type;
-    bool hold_bool_val;
-    long hold_long_val;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    int esa_ptr;
-#endif
-
-    make_alias(name, alias);
-    if (flash_get_config(name, &val, CONFIG_STRING)) {
-        return val;
-    } else {
-        dp = flash_lookup_config(alias);
-        if (dp) {
-            val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
-            switch (type = CONFIG_OBJECT_TYPE(dp)) {
-            case CONFIG_BOOL:
-                memcpy(&hold_bool_val, val_ptr, sizeof(bool));
-                diag_sprintf(alias_buf, "%s", hold_bool_val ? "true" : "false");
-                break;
-            case CONFIG_INT:
-                memcpy(&hold_long_val, val_ptr, sizeof(unsigned long));
-                diag_sprintf(alias_buf,"%ld", hold_long_val);
-                break;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-            case CONFIG_IP:
-                diag_sprintf(alias_buf,"%s", inet_ntoa((in_addr_t *)val_ptr));
-                break;
-            case CONFIG_ESA:
-                for (esa_ptr = 0;  esa_ptr < sizeof(enet_addr_t);  esa_ptr++) {
-                    diag_sprintf(alias_buf+(3*esa_ptr), "0x%02X", ((unsigned char *)val_ptr)[esa_ptr]);
-                    if (esa_ptr < (sizeof(enet_addr_t)-1)) diag_printf(":");
-                }
-                break;
-#endif
-            case CONFIG_SCRIPT:
-                return (char *) val_ptr;
-                break;
-            default:
-                return (char *)NULL;
-            }
-            return alias_buf;
-        } 
-        return (char *)NULL;
-    }
-}
-
-#endif //  CYGSEM_REDBOOT_FLASH_ALIASES
-
-//
-// Write the in-memory copy of the configuration data to the flash device.
-//
-void
-flash_write_config(void)
-{
-#ifndef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
-    int stat;
-    void *err_addr;
-#endif
-
-    config->len = sizeof(struct _config);
-    config->key1 = CONFIG_KEY1;  
-    config->key2 = CONFIG_KEY2;
-    config->cksum = cyg_crc32((unsigned char *)config, sizeof(struct _config)-sizeof(config->cksum));
-    if (verify_action("Update RedBoot non-volatile configuration")) {
-#ifdef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
-        memcpy(fis_work_block, fis_addr, fisdir_size);
-        fis_update_directory();
-#else //  CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
-#ifdef CYGSEM_REDBOOT_FLASH_LOCK_SPECIAL
-        // Insure [quietly] that the config page is unlocked before trying to update
-        flash_unlock((void *)cfg_base, cfg_size, (void **)&err_addr);
-#endif
-        if ((stat = flash_erase(cfg_base, cfg_size, (void **)&err_addr)) != 0) {
-            diag_printf("   initialization failed at %p: %s\n", err_addr, flash_errmsg(stat));
-        } else {
-            if ((stat = flash_program(cfg_base, (void *)config, sizeof(struct _config), 
-                                      (void **)&err_addr)) != 0) {
-                diag_printf("Error writing config data at %p: %s\n", 
-                            err_addr, flash_errmsg(stat));
-            }
-        }
-#ifdef CYGSEM_REDBOOT_FLASH_LOCK_SPECIAL
-        // Insure [quietly] that the config data is locked after the update
-        flash_lock((void *)cfg_base, cfg_size, (void **)&err_addr);
-#endif
-#endif
-    }
-}
-
-//
-// Find the configuration entry for a particular key
-//
-static unsigned char *
-flash_lookup_config(char *key)
-{
-    unsigned char *dp;
-    int len;
-
-    if (!config_ok) return (unsigned char *)NULL;
-
-    dp = &config->config_data[0];
-    while (dp < &config->config_data[sizeof(config->config_data)]) {
-        len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) +
-            config_length(CONFIG_OBJECT_TYPE(dp));
-        if (strcmp(key, CONFIG_OBJECT_KEY(dp)) == 0) {
-            return dp;
-        }
-        dp += len;
-    }
-//    diag_printf("Can't find config data for '%s'\n", key);
-    return false;
-}
-
-//
-// Retrieve a data object from the data base (in memory copy)
-//
-bool
-flash_get_config(char *key, void *val, int type)
-{
-    unsigned char *dp;
-    void *val_ptr;
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
-    struct _config *save_config = 0;
-#endif
-
-    if (!config_ok) return false;
-
-    if ((dp = flash_lookup_config(key)) != (unsigned char *)NULL) {
-        if (CONFIG_OBJECT_TYPE(dp) == type) {
-            val_ptr = (void *)CONFIG_OBJECT_VALUE(dp);
-            switch (type) {
-                // Note: the data may be unaligned in the configuration data
-            case CONFIG_BOOL:
-                memcpy(val, val_ptr, sizeof(bool));
-                break;
-            case CONFIG_INT:
-                memcpy(val, val_ptr, sizeof(unsigned long));
-                break;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-            case CONFIG_IP:
-                memcpy(val, val_ptr, sizeof(in_addr_t));
-                break;
-            case CONFIG_ESA:
-                memcpy(val, val_ptr, sizeof(enet_addr_t));
-                break;
-#endif
-#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
-	    case CONFIG_NETPORT:
-#endif
-            case CONFIG_STRING:
-            case CONFIG_SCRIPT:
-                // Just return a pointer to the script/line
-                *(unsigned char **)val = (unsigned char *)val_ptr;
-                break;
-            }
-        } else {
-            diag_printf("Request for config value '%s' - wrong type\n", key);
-        }
-        return true;
-    }
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
-    // Did not find key. Is configuration data valid?
-    // Check to see if the config data is valid, if not, revert to 
-    // readonly mode, by setting config to readonly_config.  We
-    // will set it back before we leave this function.
-    if ( (config != readonly_config) && ((cyg_crc32((unsigned char *)config, 
-               sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
-        (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2))) {
-        save_config = config;
-        config = readonly_config;
-        if ((cyg_crc32((unsigned char *)config, 
-                       sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
-            (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2)) {
-            diag_printf("FLASH configuration checksum error or invalid key\n");
-            config = save_config;
-            return false;
-        }
-        else{
-            diag_printf("Getting config information in READONLY mode\n");
-            return flash_get_config(key, val, type);
-        }        
-    }
-#endif
-    return false;
-}
-
-//
-// Copy data into the config area
-//
-static void
-flash_config_insert_value(unsigned char *dp, struct config_option *opt)
-{
-    switch (opt->type) {
-        // Note: the data may be unaligned in the configuration data
-    case CONFIG_BOOL:
-        memcpy(dp, (void *)&opt->dflt, sizeof(bool));
-        break;
-    case CONFIG_INT:
-        memcpy(dp, (void *)&opt->dflt, sizeof(unsigned long));
-        break;
-#ifdef CYGPKG_REDBOOT_NETWORKING
-    case CONFIG_IP:
-        memcpy(dp, (void *)&opt->dflt, sizeof(in_addr_t));
-        break;
-    case CONFIG_ESA:
-        memcpy(dp, (void *)opt->dflt, sizeof(enet_addr_t));
-        break;
-#if defined(CYGHWR_NET_DRIVERS) && (CYGHWR_NET_DRIVERS > 1)
-    case CONFIG_NETPORT:
-	// validate dflt and if not acceptable use first port
-        {
-	    int index;
-	    const char *name;
-	    for (index = 0; (name = net_devname(index)) != NULL; index++)
-		if (!strcmp((char *)opt->dflt, name))
-		    break;
-	    if (name == NULL)
-		name = net_devname(0);
-	    memcpy(dp, name, strlen(name) + 1);
-        }
-        break;
-#endif
-#endif
-    case CONFIG_STRING:
-        memcpy(dp, (void *)opt->dflt, config_length(CONFIG_STRING));
-        break;
-    case CONFIG_SCRIPT:
-        break;
-    }
-}
-
-//
-// Add a new option to the database
-//
-bool
-flash_add_config(struct config_option *opt, bool update)
-{
-    unsigned char *dp, *kp;
-    int len, elen, size;
-
-    // If data item is already present, just update it
-    // Note: only the data value can be thusly changed
-    if ((dp = flash_lookup_config(opt->key)) != (unsigned char *)NULL) {
-        flash_config_insert_value(CONFIG_OBJECT_VALUE(dp), opt);
-        if (update) {
-            flash_write_config();
-        }
-        return true;
-    }
-    // Add the data item
-    dp = &config->config_data[0];
-    size = 0;
-    while (size < sizeof(config->config_data)) {
-        if (CONFIG_OBJECT_TYPE(dp) == CONFIG_EMPTY) {
-            kp = opt->key;
-            len = strlen(kp) + 1;
-            size += len + 2 + 2 + config_length(opt->type);
-            if (opt->enable) {
-                elen = strlen(opt->enable) + 1;
-                size += elen;
-            } else {
-                elen = 0;
-            }
-            if (size > sizeof(config->config_data)) {
-                break;
-            }
-            CONFIG_OBJECT_TYPE(dp) = opt->type; 
-            CONFIG_OBJECT_KEYLEN(dp) = len;
-            CONFIG_OBJECT_ENABLE_SENSE(dp) = opt->enable_sense;
-            CONFIG_OBJECT_ENABLE_KEYLEN(dp) = elen;
-            dp = CONFIG_OBJECT_KEY(dp);
-            while (*kp) *dp++ += *kp++;
-            *dp++ = '\0';    
-            if (elen) {
-                kp = opt->enable;
-                while (*kp) *dp++ += *kp++;
-                *dp++ = '\0';    
-            }
-            flash_config_insert_value(dp, opt);
-            if (update) {
-                flash_write_config();
-            }
-            return true;
-        } else {
-            len = 4 + CONFIG_OBJECT_KEYLEN(dp) + CONFIG_OBJECT_ENABLE_KEYLEN(dp) +
-                config_length(CONFIG_OBJECT_TYPE(dp));
-            dp += len;
-            size += len;
-        }
-    }
-    diag_printf("No space to add '%s'\n", opt->key);
-    return false;
-}
-
-//
-// Reset/initialize configuration data - used only when starting from scratch
-//
-static void
-config_init(void)
-{
-    // Well known option strings
-    struct config_option *optend = __CONFIG_options_TAB_END__;
-    struct config_option *opt = __CONFIG_options_TAB__;
-
-    memset(config, 0, sizeof(struct _config));
-    while (opt != optend) {
-        if (!flash_add_config(opt, false)) {
-            return;
-        }
-        opt++;
-    }
-    config_ok = true;
-}
-
-//
-// Attempt to get configuration information from the FLASH.
-// If available (i.e. good checksum, etc), initialize "known"
-// values for later use.
-//
-static void
-load_flash_config(void)
-{
-    bool use_boot_script;
-
-    config_ok = false;
-    script = (unsigned char *)0;
-    if (!do_flash_init()) return;
-    config = (struct _config *)(workspace_end-sizeof(struct _config));
-    backup_config = (struct _config *)((CYG_ADDRESS)config-sizeof(struct _config));
-    workspace_end = (unsigned char *)backup_config;
-    cfg_size = (flash_block_size > sizeof(struct _config)) ? 
-        sizeof(struct _config) : 
-        _rup(sizeof(struct _config), flash_block_size);
-#ifdef CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG
-    cfg_size = _rup(cfg_size, sizeof(struct fis_image_desc));
-    if ((flash_block_size-cfg_size) < 8*sizeof(struct fis_image_desc)) {
-        // Too bad this can't be checked at compile/build time
-        diag_printf("Sorry, FLASH config exceeds available space in FIS directory\n");
-        return;
-    }
-    fisdir_size = flash_block_size - cfg_size;
-    cfg_base = (void *)(((CYG_ADDRESS)fis_addr + flash_block_size) - cfg_size);
-#else
-    if (CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK < 0) {
-        cfg_base = (void *)((CYG_ADDRESS)flash_end + 1 -
-           _rup(_rup((-CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK*flash_block_size), cfg_size), flash_block_size));
-    } else {
-        cfg_base = (void *)((CYG_ADDRESS)flash_start + 
-           _rup(_rup((CYGNUM_REDBOOT_FLASH_CONFIG_BLOCK*flash_block_size), cfg_size), flash_block_size));
-    }
-#endif
-#ifdef CYGSEM_REDBOOT_FLASH_CONFIG_READONLY_FALLBACK
-    readonly_config = cfg_base;
-#endif
-    memcpy(config, cfg_base, sizeof(struct _config));
-    if ((cyg_crc32((unsigned char *)config, 
-                   sizeof(struct _config)-sizeof(config->cksum)) != config->cksum) ||
-        (config->key1 != CONFIG_KEY1)|| (config->key2 != CONFIG_KEY2)) {
-        diag_printf("FLASH configuration checksum error or invalid key\n");
-        config_init();
-        return;
-    }
-    config_ok = true;
-    flash_get_config("boot_script", &use_boot_script, CONFIG_BOOL);
-    if (use_boot_script) {
-        flash_get_config("boot_script_data", &script, CONFIG_SCRIPT);
-        flash_get_config("boot_script_timeout", &script_timeout, CONFIG_INT);
-    }
-#ifdef CYGSEM_REDBOOT_VARIABLE_BAUD_RATE
-    if (flash_get_config("console_baud_rate", &console_baud_rate, CONFIG_INT)) {
-        extern int set_console_baud_rate(int);
-        set_console_baud_rate(console_baud_rate);
-    }
-#endif
-}
-
-RedBoot_init(load_flash_config, RedBoot_INIT_FIRST);
-
-#endif // CYGSEM_REDBOOT_FLASH_CONFIG
-
 // EOF flash.c
--- a/packages/redboot/current/src/load.c
+++ b/packages/redboot/current/src/load.c
@@ -375,7 +375,7 @@ load_elf_image(getc_t getc, unsigned lon
             // Copy data into memory
             while (len-- > 0) {
 #ifdef CYGSEM_REDBOOT_VALIDATE_USER_RAM_LOADS
-                if ((addr < user_ram_start) || (addr > user_ram_end)) {
+                if (!valid_address(addr)) {
                     redboot_getc_terminate(true);
                     diag_printf("*** Abort! Attempt to load ELF data to address: %p which is not in RAM\n", (void*)addr);
                     return 0;
@@ -502,7 +502,7 @@ load_srec_image(getc_t getc, unsigned lo
                 lowest_address = (unsigned long)(addr - addr_offset);
             }
 #ifdef CYGSEM_REDBOOT_VALIDATE_USER_RAM_LOADS
-            if ((addr < user_ram_start) || (addr > user_ram_end)) {
+            if (!valid_address(addr)) {
 	      // Only if there is no need to stop the download before printing
 	      // output can we ask confirmation questions.
                 redboot_getc_terminate(true);
@@ -707,9 +707,7 @@ do_load(int argc, char *argv[])
         diag_printf("Using default protocol (%s)\n", which);
     }
 #ifdef CYGSEM_REDBOOT_VALIDATE_USER_RAM_LOADS
-    if (base_addr_set &&
-        ((base < (unsigned long)user_ram_start) ||
-         (base > (unsigned long)user_ram_end))) {
+    if (base_addr_set && !valid_address(base)) {
         if (!verify_action("Specified address (%p) is not believed to be in RAM", (void*)base))
             return;
         spillover_ok = true;
@@ -736,7 +734,7 @@ do_load(int argc, char *argv[])
         err = 0;
         while ((res = redboot_getc()) >= 0) {
 #ifdef CYGSEM_REDBOOT_VALIDATE_USER_RAM_LOADS
-            if (mp >= user_ram_end && !spillover_ok) {
+            if (!valid_address(mp) && !spillover_ok) {
                 // Only if there is no need to stop the download
                 // before printing output can we ask confirmation
                 // questions.
--- a/packages/redboot/current/src/main.c
+++ b/packages/redboot/current/src/main.c
@@ -9,7 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003 Red Hat, Inc.
-// Copyright (C) 2002 Gary Thomas
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -142,10 +142,25 @@ extern struct idle_tab_entry __RedBoot_I
 extern void HAL_ARCH_PROGRAM_NEW_STACK(void *fun);
 #endif
 
+// 
+// [Null] Builtin [Power On] Self Test
+//
+void bist(void) CYGBLD_ATTRIB_WEAK;
 
 void
+bist(void) 
+{
+}
+
+//
+// 'version' command
+//
+void
 do_version(int argc, char *argv[])
 {
+#if CYGBLD_REDBOOT_MAX_MEM_SEGMENTS > 1
+    int seg;
+#endif
 #ifdef CYGPKG_REDBOOT_FLASH
     externC void _flash_info(void);
 #endif
@@ -156,14 +171,26 @@ do_version(int argc, char *argv[])
     diag_printf("Platform: %s (%s) %s\n", HAL_PLATFORM_BOARD, HAL_PLATFORM_CPU, HAL_PLATFORM_EXTRA);
 #endif
     diag_printf("Copyright (C) 2000, 2001, 2002, Red Hat, Inc.\n\n");
-    diag_printf("RAM: %p-%p, %p-%p available\n", 
-                (void*)ram_start, (void*)ram_end,
-                (void*)user_ram_start, (void *)user_ram_end);
+    diag_printf("RAM: %p-%p, ", (void*)ram_start, (void*)ram_end);
+    diag_printf("[%p-%p]", mem_segments[0].start, mem_segments[0].end);
+#if CYGBLD_REDBOOT_MAX_MEM_SEGMENTS > 1
+    for (seg = 1;  seg < CYGBLD_REDBOOT_MAX_MEM_SEGMENTS;  seg++) {
+        if (mem_segments[seg].start != NO_MEMORY) {
+            diag_printf("[%p-%p]", mem_segments[seg].start, mem_segments[seg].end);
+        }
+    }
+#endif
+    diag_printf(" available\n");
 #ifdef CYGPKG_REDBOOT_FLASH
     _flash_info();
 #endif
 }
 
+//
+// This function is called when RedBoot is idle (waiting for user
+// input).  It will call any registered "idle" routines, e.g. scan
+// for incoming network connections, blank an LCD screen, etc.
+//
 void
 do_idle(bool is_idle)
 {
@@ -199,6 +226,9 @@ cyg_start(void)
     int cur;
     struct init_tab_entry *init_entry;
     extern char RedBoot_version[];
+#if CYGBLD_REDBOOT_MAX_MEM_SEGMENTS > 1
+    int seg;
+#endif
 
     // Export version information
     CYGACC_CALL_IF_MONITOR_VERSION_SET(RedBoot_version);
@@ -245,6 +275,9 @@ cyg_start(void)
         workspace_size = workspace_end - workspace_start;
     }
 
+    // Nothing has ever been loaded into memory
+    entry_address = NO_MEMORY;
+
     bist();
 
 #ifdef CYGOPT_REDBOOT_FIS_ZLIB_COMMON_BUFFER
@@ -256,9 +289,17 @@ cyg_start(void)
         (*init_entry->fun)();
     }
 
-    user_ram_start = workspace_start;
-    user_ram_end = workspace_end;
+    mem_segments[0].start = workspace_start;
+    mem_segments[0].end = workspace_end;
+#if CYGBLD_REDBOOT_MAX_MEM_SEGMENTS > 1
+    for (seg = 1;  seg < CYGBLD_REDBOOT_MAX_MEM_SEGMENTS;  seg++) {
+        cyg_plf_memory_segment(seg, &mem_segments[seg].start, &mem_segments[seg].end);
+    }
+#endif
 
+#ifdef CYGSEM_REDBOOT_PLF_STARTUP
+    cyg_plf_redboot_startup();
+#endif
     do_version(0,0);
 
 #ifdef CYGFUN_REDBOOT_BOOT_SCRIPT
@@ -435,6 +476,11 @@ return_to_redboot(int status)
     CYGARC_HAL_RESTORE_GP();
 }
 
+#if 0
+externC _get_cache_contents(unsigned char *buf);
+unsigned char _hold_cache_contents[2][256*2*8];
+#endif
+
 void
 do_go(int argc, char *argv[])
 {
@@ -466,6 +512,10 @@ do_go(int argc, char *argv[])
     {
         return;
     }
+    if (entry == (unsigned long)NO_MEMORY) {
+        diag_printf("No entry point known - aborted\n");
+        return;
+    }
     if (wait_time_set) {
         int script_timeout_ms = wait_time * 1000;
 #ifdef CYGSEM_REDBOOT_FLASH_CONFIG
@@ -504,6 +554,9 @@ do_go(int argc, char *argv[])
 #endif
 	
     HAL_DISABLE_INTERRUPTS(oldints);
+#if 0
+    _get_cache_contents(CYGARC_UNCACHED_ADDRESS(&_hold_cache_contents[0][0]));
+#endif
     HAL_DCACHE_SYNC();
     if (!cache_enabled) {
 	HAL_ICACHE_DISABLE();
@@ -512,7 +565,13 @@ do_go(int argc, char *argv[])
     }
     HAL_ICACHE_INVALIDATE_ALL();
     HAL_DCACHE_INVALIDATE_ALL();
-
+#if 0
+    _get_cache_contents(CYGARC_UNCACHED_ADDRESS(&_hold_cache_contents[1][0]));
+    diag_printf("Cache before flush/invalidate\n");
+    diag_dump_buf(&_hold_cache_contents[0][0], sizeof(_hold_cache_contents[0]));
+    diag_printf("Cache after flush/invalidate\n");
+    diag_dump_buf(&_hold_cache_contents[1][0], sizeof(_hold_cache_contents[1]));
+#endif
     // set up a temporary context that will take us to the trampoline
     HAL_THREAD_INIT_CONTEXT((CYG_ADDRESS)workspace_end, entry, trampoline, 0);
 
@@ -659,12 +718,20 @@ do_baud_rate(int argc, char *argv[])
 }
 #endif
 
-// 
-// [Null] Builtin [Power On] Self Test
+//
+// Validate an address to see if it is within any known RAM area
 //
-void bist(void) CYGBLD_ATTRIB_WEAK;
+bool
+valid_address(unsigned char *addr)
+{
+    int seg;
 
-void
-bist(void) 
-{
+    for (seg = 0;  seg < CYGBLD_REDBOOT_MAX_MEM_SEGMENTS;  seg++) {
+        if (mem_segments[seg].start != NO_MEMORY) {
+            if ((addr >= mem_segments[seg].start) && (addr < mem_segments[seg].end)) {
+                return true;
+            }
+        }
+    }
+    return false;
 }
--- a/packages/redboot/current/src/net/net_io.c
+++ b/packages/redboot/current/src/net/net_io.c
@@ -119,7 +119,7 @@ RedBoot_config_option("Gateway IP addres
 #endif
 RedBoot_config_option("Default server IP address",
                       bootp_server_ip,
-                      "bootp", false,
+                      ALWAYS_ENABLED, true,
                       CONFIG_IP,
                       0
     );
@@ -685,8 +685,6 @@ net_init(void)
         flash_get_IP("bootp_my_ip_mask", &__local_ip_mask);
         flash_get_IP("bootp_my_gateway_ip", &__local_ip_gate);
 #endif
-        flash_get_config("bootp_server_ip", &my_bootp_info.bp_siaddr,
-                         CONFIG_IP);
     }
 #endif
 # ifdef CYGDBG_IO_ETH_DRIVERS_DEBUG
@@ -777,6 +775,9 @@ net_init(void)
                     __local_enet_addr[4],
                     __local_enet_addr[5]);
 
+#ifdef CYGSEM_REDBOOT_FLASH_CONFIG
+        flash_get_IP("bootp_server_ip", &my_bootp_info.bp_siaddr);
+#endif
 #ifdef CYGPKG_REDBOOT_NETWORKING_DNS
 	redboot_dns_res_init();
 #endif
--- a/packages/redboot/current/src/net/tftp_client.c
+++ b/packages/redboot/current/src/net/tftp_client.c
@@ -9,7 +9,7 @@
 // -------------------------------------------
 // This file is part of eCos, the Embedded Configurable Operating System.
 // Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
-// Copyright (C) 2002 Gary Thomas
+// Copyright (C) 2002, 2003 Gary Thomas
 //
 // eCos is free software; you can redistribute it and/or modify it under
 // the terms of the GNU General Public License as published by the Free
@@ -191,12 +191,13 @@ tftp_stream_read(char *buf,
                 // Out of data
                 break;
             }
-            timeout.tv_sec = TFTP_TIMEOUT_PERIOD;
+            timeout.tv_sec = (tftp_stream.last_good_block == 0) ? 10*TFTP_TIMEOUT_PERIOD : TFTP_TIMEOUT_PERIOD;
             timeout.tv_usec = 0;
             recv_len = sizeof(tftp_stream.data);
             if ((data_len = __udp_recvfrom(&tftp_stream.data[0], recv_len, &tftp_stream.from_addr, 
                                            &tftp_stream.local_addr,  &timeout)) < 0) {
                 // No data, try again
+                diag_printf("TFTP timed out %d/%d\n", tftp_stream.total_timeouts+1, TFTP_TIMEOUT_MAX);
                 if ((++tftp_stream.total_timeouts > TFTP_TIMEOUT_MAX) || 
                     (tftp_stream.last_good_block == 0)) {
                     // Timeout - no data received
new file mode 100644
--- /dev/null
+++ b/packages/redboot/current/src/time_date.cxx
@@ -0,0 +1,124 @@
+//==========================================================================
+//
+//        time_date.cxx
+//
+//        RedBoot time/date commands
+//
+//==========================================================================
+//####ECOSGPLCOPYRIGHTBEGIN####
+// -------------------------------------------
+// This file is part of eCos, the Embedded Configurable Operating System.
+// Copyright (C) 2003 Gary Thomas
+//
+// eCos is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 or (at your option) any later version.
+//
+// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with eCos; if not, write to the Free Software Foundation, Inc.,
+// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// As a special exception, if other files instantiate templates or use macros
+// or inline functions from this file, or you compile this file and link it
+// with other works to produce a work based on this file, this file does not
+// by itself cause the resulting work to be covered by the GNU General Public
+// License. However the source code for this file must still be made available
+// in accordance with section (3) of the GNU General Public License.
+//
+// This exception does not invalidate any other reasons why a work based on
+// this file might be covered by the GNU General Public License.
+//
+// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
+// at http://sources.redhat.com/ecos/ecos-license/
+// -------------------------------------------
+//####ECOSGPLCOPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):     gthomas
+// Contributors:  
+// Date:          2003-09-10
+// Description:   
+//####DESCRIPTIONEND####
+// -------------------------------------------------------------------------
+
+#include <redboot.h>
+#include <pkgconf/hal.h>
+#include <pkgconf/wallclock.h>
+
+#include <cyg/infra/diag.h>
+#include <cyg/io/wallclock.hxx>              // The WallClock API
+#include <cyg/io/wallclock/wallclock.inl>    // Helper functions (avoids LIBC)
+
+RedBoot_cmd("date", 
+            "Show/Set the time of day", 
+            "[HH:MM:SS MM/DD/YY]",
+            do_time_date
+    );
+
+static bool
+verify(cyg_uint32 val, int min, int max, char *id)
+{
+    if (((int)val < min) || ((int)val > max)) {
+        diag_printf("%s is out of range - must be [%d..%d]\n", id, min, max);
+        return false;
+    }
+    return true;
+}
+
+void
+do_time_date(int argc, char *argv[])
+{
+    cyg_uint32 now = Cyg_WallClock::wallclock->get_current_time();
+    cyg_uint32 year, month, mday, hour, minute, second;
+    char *sp;
+    bool ok = true;
+
+    if (argc == 1) {
+        // Just show the current time/date
+        _simple_mkdate(now, &year, &month, &mday, &hour, &minute, &second);
+        diag_printf("%02d:%02d:%02d %d/%02d/%d\n", 
+                    hour, minute, second, month, mday, year);
+    } else if (argc == 3) {
+        sp = argv[1];
+        if (!parse_num(sp, (unsigned long *)&hour, &sp, ":") ||
+            !parse_num(sp, (unsigned long *)&minute, &sp, ":") ||
+            !parse_num(sp, (unsigned long *)&second, &sp, ":")) {
+            ok = false;
+        }
+        sp = argv[2];
+        if (!parse_num(sp, (unsigned long *)&month, &sp, "/") ||
+            !parse_num(sp, (unsigned long *)&mday, &sp, "/") ||
+            !parse_num(sp, (unsigned long *)&year, &sp, "/")) {
+            ok = false;
+        }
+        if (ok) {
+            // Verify values make some sense, then set the hardware
+            ok = ok && verify(hour, 0, 23, "hour");
+            ok = ok && verify(minute, 0, 59, "minute");
+            ok = ok && verify(second, 0, 59, "second");
+            ok = ok && verify(month, 1, 12, "month");
+            ok = ok && verify(mday, 1, 31, "day");
+            if (year < 100) year += 2000;
+            ok = ok && verify(year, 2000, 2034, "year");
+            if (ok) {
+                now = _simple_mktime(year, month, mday, hour, minute, second);
+                Cyg_WallClock::wallclock->set_current_time(now);
+            }
+        }
+    } else {
+        ok = false;
+    }
+    if (!ok) {
+        diag_printf("usage: date [HH:MM:SS MM/DD/YY]\n");
+    }
+
+}
+
+// -------------------------------------------------------------------------
+// EOF time_date.cxx