changeset 178:aa8364213009

Merge from eCos master repository on 2001-08-15-01:50:29-BST
author jlarmour
date Wed, 15 Aug 2001 02:21:28 +0000
parents 4c750ce71ae3
children 391299f9e541
files packages/devs/eth/smsc/lan91cxx/current/ChangeLog packages/devs/eth/smsc/lan91cxx/current/src/smsc_lan91cxx.h packages/devs/serial/arm/at91/current/ChangeLog packages/devs/serial/arm/at91/current/src/at91_serial.c packages/hal/arm/arm9/var/current/ChangeLog packages/hal/arm/arm9/var/current/cdl/hal_arm_arm9.cdl packages/hal/arm/arm9/var/current/include/hal_cache.h packages/hal/i386/pc/current/ChangeLog packages/hal/i386/pc/current/cdl/hal_i386_pc.cdl packages/kernel/current/ChangeLog packages/kernel/current/cdl/kernel.cdl packages/kernel/current/cdl/synch.cdl packages/kernel/current/include/smp.hxx packages/kernel/current/src/common/kapi.cxx packages/kernel/current/tests/kmutex3.c packages/kernel/current/tests/mutex3.cxx packages/net/snmp/agent/current/ChangeLog packages/net/snmp/agent/current/cdl/snmpagent.cdl packages/net/snmp/agent/current/tests/snmpping.c packages/redboot/current/ChangeLog packages/redboot/current/src/io.c
diffstat 21 files changed, 962 insertions(+), 71 deletions(-) [+]
line wrap: on
line diff
--- a/packages/devs/eth/smsc/lan91cxx/current/ChangeLog
+++ b/packages/devs/eth/smsc/lan91cxx/current/ChangeLog
@@ -1,3 +1,9 @@
+2001-08-13  Hugo Tyson  <hmt@redhat.com>
+
+	* src/smsc_lan91cxx.h (get_att,put_att): Condition out the inline
+	functions if not CYGINT_DEVS_ETH_SMSC_LAN91CXX_PCMCIA_MODE -
+	because they don't compile.  Inlines are not like macros.
+
 2001-07-27  Jordi Colomer  <jco@ict.es>
 
 	* cdl/smsc_lan91cxx_eth_drivers.cdl:
--- a/packages/devs/eth/smsc/lan91cxx/current/src/smsc_lan91cxx.h
+++ b/packages/devs/eth/smsc/lan91cxx/current/src/smsc_lan91cxx.h
@@ -350,6 +350,7 @@ get_banksel(struct eth_drv_sc *sc)
 
 // ------------------------------------------------------------------------
 // Write on PCMCIA attribute memory
+#if CYGINT_DEVS_ETH_SMSC_LAN91CXX_PCMCIA_MODE					
 static __inline__ void
 put_att(struct eth_drv_sc *sc, int offs, unsigned char val)
 {
@@ -377,6 +378,7 @@ get_att(struct eth_drv_sc *sc, int offs)
 #endif
     return val;
 }
+#endif // #if CYGINT_DEVS_ETH_SMSC_LAN91CXX_PCMCIA_MODE					
 
 // ------------------------------------------------------------------------
 #endif CYGONCE_DEVS_ETH_SMSC_LAN91CXX_LAN91CXX_H
--- a/packages/devs/serial/arm/at91/current/ChangeLog
+++ b/packages/devs/serial/arm/at91/current/ChangeLog
@@ -1,3 +1,8 @@
+2001-08-14  Jonathan Larmour  <jlarmour@redhat.com>
+
+	* src/at91_serial.c (at91_serial_stop_xmit): Write to IDR, not IER.
+	(at91_serial_ISR): Return CYG_ISR_HANDLED.
+
 2001-07-24  Gary Thomas  <gthomas@redhat.com>
 
 	* src/at91_serial.h: 
--- a/packages/devs/serial/arm/at91/current/src/at91_serial.c
+++ b/packages/devs/serial/arm/at91/current/src/at91_serial.c
@@ -317,7 +317,7 @@ at91_serial_stop_xmit(serial_channel *ch
     at91_serial_info *at91_chan = (at91_serial_info *)chan->dev_priv;
     CYG_ADDRWORD base = at91_chan->base;
 
-    HAL_WRITE_UINT32(base+AT91_US_IER, AT91_US_IER_TxRDY);
+    HAL_WRITE_UINT32(base+AT91_US_IDR, AT91_US_IER_TxRDY);
 }
 
 // Serial I/O - low level interrupt handler (ISR)
@@ -326,7 +326,7 @@ at91_serial_ISR(cyg_vector_t vector, cyg
 {
     cyg_drv_interrupt_mask(vector);
     cyg_drv_interrupt_acknowledge(vector);
-    return CYG_ISR_CALL_DSR;  // Cause DSR to be run
+    return (CYG_ISR_CALL_DSR|CYG_ISR_HANDLED);  // Cause DSR to be run
 }
 
 // Serial I/O - high level interrupt handler (DSR)
--- a/packages/hal/arm/arm9/var/current/ChangeLog
+++ b/packages/hal/arm/arm9/var/current/ChangeLog
@@ -1,3 +1,7 @@
+2001-08-13  Jesper Skov  <jskov@redhat.com>
+
+	* include/hal_cache.h: Support ARM variants 920, 922, 925 and 940.
+
 2001-04-30  Gary Thomas  <gthomas@redhat.com>
 
 	* src/arm9_misc.c (hal_hardware_init): Use CDL configuration to
--- a/packages/hal/arm/arm9/var/current/cdl/hal_arm_arm9.cdl
+++ b/packages/hal/arm/arm9/var/current/cdl/hal_arm_arm9.cdl
@@ -54,4 +54,54 @@ cdl_package CYGPKG_HAL_ARM_ARM9 {
 
     compile       arm9_misc.c
 
+    cdl_interface CYGINT_HAL_ARM_ARM9_VARIANT {
+        display  "Number of variant implementations in this configuration"
+        no_define
+        requires 1 == CYGINT_HAL_ARM_ARM9_VARIANT
+    }
+
+    # CPU variant supported
+    cdl_option CYGPKG_HAL_ARM_ARM9_ARM920T {
+        display       "ARM ARM920T microprocessor"
+        implements    CYGINT_HAL_ARM_ARM9_VARIANT
+        default_value 0
+        no_define
+        define        -file=system.h CYGPKG_HAL_ARM_ARM9_ARM920T
+        description "
+            The ARM920T has 16k data cache, 16k instruction cache, 16 word
+            write buffer and an MMU."
+    }
+
+    cdl_option CYGPKG_HAL_ARM_ARM9_ARM922T {
+        display       "ARM ARM922T microprocessor"
+        implements    CYGINT_HAL_ARM_ARM9_VARIANT
+        default_value 0
+        no_define
+        define        -file=system.h CYGPKG_HAL_ARM_ARM9_ARM922T
+        description "
+            The ARM922T has 8k data cache, 8k instruction cache, 16 word
+            write buffer and an MMU."
+    }
+
+    cdl_option CYGPKG_HAL_ARM_ARM9_ARM925T {
+        display       "ARM ARM925T microprocessor"
+        implements    CYGINT_HAL_ARM_ARM9_VARIANT
+        default_value 0
+        no_define
+        define        -file=system.h CYGPKG_HAL_ARM_ARM9_ARM925T
+        description "
+            The ARM925T has 8k data cache, 16k instruction cache, 16 word
+            write buffer and an MMU."
+    }
+
+    cdl_option CYGPKG_HAL_ARM_ARM9_ARM940T {
+        display       "ARM ARM940T microprocessor"
+        implements    CYGINT_HAL_ARM_ARM9_VARIANT
+        default_value 0
+        no_define
+        define        -file=system.h CYGPKG_HAL_ARM_ARM9_ARM940T
+        description "
+            The ARM920T has 4k data cache, 4k instruction cache, 8 word
+            write buffer and a protection unit."
+    }
 }
--- a/packages/hal/arm/arm9/var/current/include/hal_cache.h
+++ b/packages/hal/arm/arm9/var/current/include/hal_cache.h
@@ -57,15 +57,75 @@
 //-----------------------------------------------------------------------------
 // Cache dimensions
 
-#define HAL_ICACHE_SIZE                 0x4000
-#define HAL_ICACHE_LINE_SIZE            16
-#define HAL_ICACHE_WAYS                 2
-#define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
+#if defined(CYGPKG_HAL_ARM_ARM9_ARM920T)
+# define HAL_ICACHE_SIZE                 0x4000
+# define HAL_ICACHE_LINE_SIZE            32
+# define HAL_ICACHE_WAYS                 64
+# define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
+
+# define HAL_DCACHE_SIZE                 0x4000
+# define HAL_DCACHE_LINE_SIZE            32
+# define HAL_DCACHE_WAYS                 64
+# define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
+
+# define HAL_WRITE_BUFFER                64
+
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_STEP  0x20
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_LIMIT 0xe0
+
+#elif defined(CYGPKG_HAL_ARM_ARM9_ARM922T)
+# define HAL_ICACHE_SIZE                 0x2000
+# define HAL_ICACHE_LINE_SIZE            32
+# define HAL_ICACHE_WAYS                 64
+# define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
+
+# define HAL_DCACHE_SIZE                 0x2000
+# define HAL_DCACHE_LINE_SIZE            32
+# define HAL_DCACHE_WAYS                 64
+# define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
+
+# define HAL_WRITE_BUFFER                64
+
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_STEP  0x20
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_LIMIT 0x60
 
-#define HAL_DCACHE_SIZE                 0x4000
-#define HAL_DCACHE_LINE_SIZE            16
-#define HAL_DCACHE_WAYS                 2
-#define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
+#elif defined(CYGPKG_HAL_ARM_ARM9_ARM925T)
+# define HAL_ICACHE_SIZE                 0x4000
+# define HAL_ICACHE_LINE_SIZE            32
+# define HAL_ICACHE_WAYS                 2
+# define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
+
+# define HAL_DCACHE_SIZE                 0x2000
+# define HAL_DCACHE_LINE_SIZE            32
+# define HAL_DCACHE_WAYS                 2
+# define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
+
+# define HAL_WRITE_BUFFER                64
+
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE // has instruction to clean D-cache
+
+#elif defined(CYGPKG_HAL_ARM_ARM9_ARM940T)
+# define HAL_ICACHE_SIZE                 0x1000
+# define HAL_ICACHE_LINE_SIZE            16
+# define HAL_ICACHE_WAYS                 4
+# define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS))
+
+# define HAL_DCACHE_SIZE                 0x1000
+# define HAL_DCACHE_LINE_SIZE            16
+# define HAL_DCACHE_WAYS                 4
+# define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS))
+
+# define HAL_WRITE_BUFFER                32
+
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_STEP  0x10
+# define CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_LIMIT 0x40
+
+#else
+# error "No cache details defined"
+#endif
 
 // FIXME: much of the code below should make better use of
 // the definitions from hal_mmu.h
@@ -228,6 +288,7 @@ CYG_MACRO_START  /* this macro can disca
 CYG_MACRO_END
 
 // Synchronize the contents of the cache with memory.
+#ifdef CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE
 #define HAL_DCACHE_SYNC()                                               \
 CYG_MACRO_START                                                         \
     asm volatile (                                                      \
@@ -244,6 +305,33 @@ CYG_MACRO_START                         
         : "r0" /* Clobber list */                                       \
         );                                                              \
 CYG_MACRO_END
+#elif defined(CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX)
+#define HAL_DCACHE_SYNC()                                               \
+CYG_MACRO_START                                                         \
+    cyg_uint32 _tmp1, _tmp2;                                            \
+    asm volatile (                                                      \
+        "mov    %0, #0;"                                                \
+        "1: "                                                           \
+        "mov    %1, #0;"                                                \
+        "2: "                                                           \
+        "orr    r0,%0,%1;"                                              \
+        "mcr    p15,0,r0,c7,c14,2;"  /* clean index in DCache */        \
+        "add    %1,%1,%2;"                                              \
+        "cmp    %1,%3;"                                                 \
+        "bne    2b;"                                                    \
+        "add    %0,%0,#0x04000000;"  /* get to next index */            \
+        "cmp    %0,#0;"                                                 \
+        "bne    1b;"                                                    \
+        "mcr    p15,0,r0,c7,c10,4;" /* drain the write buffer */        \
+        : "=r" (_tmp1), "=r" (_tmp2)                                    \
+        : "I" (CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_STEP),            \
+          "I" (CYGHWR_HAL_ARM_ARM9_CLEAN_DCACHE_INDEX_LIMIT)            \
+        : "r0" /* Clobber list */                                       \
+        );                                                              \
+CYG_MACRO_END
+#else
+# error "Don't know how to sync Dcache"
+#endif
 
 // Set the data cache refill burst size
 //#define HAL_DCACHE_BURST_SIZE(_size_)
--- a/packages/hal/i386/pc/current/ChangeLog
+++ b/packages/hal/i386/pc/current/ChangeLog
@@ -1,3 +1,7 @@
+2001-08-13  Jonathan Larmour  <jlarmour@redhat.com>
+
+	* cdl/hal_i386_pc.cdl: Fix CYG_HAL_STARTUP description.
+
 2001-07-13  Nick Garnett  <nickg@redhat.com>
 
 	* cdl/hal_i386_pc.cdl: Added requires statement to
--- a/packages/hal/i386/pc/current/cdl/hal_i386_pc.cdl
+++ b/packages/hal/i386/pc/current/cdl/hal_i386_pc.cdl
@@ -75,9 +75,13 @@ cdl_package CYGPKG_HAL_I386_PC {
 	no_define
 	define -file system.h CYG_HAL_STARTUP
         description   "
-            At the moment only RAM startup is supported. This should
-            be extended to include ROM startup which would be used to
-            test early initialization code copying data/code to \"RAM\"."
+            It is possible to configure eCos for the PC target to build for
+            RAM startup (generally when being run under an existing
+            Monitor program like RedBoot), FLOPPY startup (for writing
+            to a floppy disk, which can then be used for booting
+            on PCs with a standard BIOS), or ROM startup (for writing
+            straight to a boot ROM/Flash). ROM startup is experimental
+            at this time."
     }
 
     cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD {
--- a/packages/kernel/current/ChangeLog
+++ b/packages/kernel/current/ChangeLog
@@ -1,3 +1,27 @@
+2001-08-14  Jonathan Larmour  <jlarmour@redhat.com>
+
+	* src/common/kapi.cxx (cyg_spinlock_spin_intsave): Cast to istate
+	to CYG_INTERRUPT_STATE * since that's what is needed.
+	(cyg_spinlock_clear_intsave): Similarly.
+
+2001-08-10  Hugo Tyson  <hmt@redhat.com>
+
+	* cdl/synch.cdl: Re-organize the options for mutexes so they are
+	active a bit more sensibly; place the default ceiling within
+	selection of ceiling protocol, and only have a default protocol if
+	there is more than one protocol active.
+
+	* tests/mutex3.cxx: More detailed handling of the possibility of
+	ceiling protocol instead of the inherit or none cases; we can run
+	the test ok and treat as inherit if the ceiling prio is higher
+	than 5, treat as none if lower than 15, and don't check anything
+	if in between - the test runs happily.
+
+	* tests/kmutex3.c (cyg_start): New test, a KAPI translation of the
+	now-classic mutex3.cxx.
+
+	* cdl/kernel.cdl: Build tests/kmutex3.c
+
 2001-08-06  Hugo Tyson  <hmt@redhat.com>
 
 	* src/sched/sched.cxx (unlock_inner): Fix assignment to current,
--- a/packages/kernel/current/cdl/kernel.cdl
+++ b/packages/kernel/current/cdl/kernel.cdl
@@ -318,14 +318,14 @@ cdl_package CYGPKG_KERNEL {
             flavor  data
             no_define
             calculated { 
-                CYGPKG_HAL_ARM_AEB ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
-                CYGPKG_HAL_ARM_EBSA285 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
-                CYGPKG_HAL_ARM_SA11X0 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
-                CYGPKG_HAL_ARM_EDB7XXX ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
-                CYGPKG_HAL_ARM_CMA230 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
-                CYGPKG_HAL_ARM_E7T ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
-                CYGPKG_HAL_ARM ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
-                "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2 tests/smp" 
+                CYGPKG_HAL_ARM_AEB ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
+                CYGPKG_HAL_ARM_EBSA285 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
+                CYGPKG_HAL_ARM_SA11X0 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
+                CYGPKG_HAL_ARM_EDB7XXX ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
+                CYGPKG_HAL_ARM_CMA230 ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
+                CYGPKG_HAL_ARM_E7T ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2" : \
+                CYGPKG_HAL_ARM ? "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone" : \
+                "tests/bin_sem0 tests/bin_sem1 tests/bin_sem2 tests/clock0 tests/clock1 tests/clockcnv tests/clocktruth tests/cnt_sem0 tests/cnt_sem1 tests/except1 tests/flag0 tests/flag1 tests/intr0 tests/kclock0 tests/kclock1 tests/kexcept1 tests/kintr0 tests/kmbox1 tests/kmutex0 tests/kmutex1 tests/kmutex3 tests/ksched1 tests/ksem0 tests/ksem1 tests/kflag0 tests/kflag1 tests/klock tests/kthread0 tests/kthread1 tests/mbox1 tests/mqueue1 tests/mutex0 tests/mutex1 tests/mutex2 tests/mutex3 tests/sched1 tests/sync2 tests/sync3 tests/thread0 tests/thread1 tests/thread2 tests/release tests/kill tests/thread_gdb tests/tm_basic tests/dhrystone tests/stress_threads tests/kcache1 tests/kcache2 tests/smp" 
             }
             description   "
                 This option specifies the set of tests for the eCos kernel."
--- a/packages/kernel/current/cdl/synch.cdl
+++ b/packages/kernel/current/cdl/synch.cdl
@@ -67,7 +67,7 @@ cdl_component CYGSEM_KERNEL_SYNCH_MUTEX_
 	    of the threads waiting for access to the mutex."
     }
 
-    cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_CEILING {
+    cdl_component CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_CEILING {
 	display       "Enable priority ceiling protocol"
 	default_value 1
 	implements CYGINT_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_COUNT	
@@ -75,6 +75,18 @@ cdl_component CYGSEM_KERNEL_SYNCH_MUTEX_
 	    This option enables priority ceiling protocol. This protocol
 	    causes the owner of a mutex to be executed at a  priority
 	    associated with the mutex."
+	cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY {
+	    display       "Default priority ceiling"
+	    flavor        data
+	    legal_values  0 to { CYGNUM_KERNEL_SCHED_PRIORITIES - 1 }
+	    default_value 0
+	    active_if     CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_CEILING
+	    description   "
+	    This option defines the default priority ceiling to be
+	    used if the chosen default priority inversion protocol is
+	    priority ceoptioniling protocol. The default value for this is zero,
+	    making all such mutexes boost threads to the maximum priority."
+	}
     }
 
     cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_NONE {
@@ -91,6 +103,7 @@ cdl_component CYGSEM_KERNEL_SYNCH_MUTEX_
     cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT {
 	display      "Default priority inversion protocol"
 	flavor       data
+	active_if      { CYGINT_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_COUNT > 1 }
 	legal_values { "INHERIT" "CEILING" "NONE" }
 	default_value { CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_INHERIT ?
                         "INHERIT" :
@@ -103,19 +116,6 @@ cdl_component CYGSEM_KERNEL_SYNCH_MUTEX_
 	    priority ceiling, or none if neither is present."
     }
 
-    cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY {
-	display       "Default priority ceiling"
-	flavor        data
-	legal_values  0 to { CYGNUM_KERNEL_SCHED_PRIORITIES - 1 }
-	default_value 0
-	active_if     { CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT == "CEILING" }
-	description   "
-	    This option defines the default priority ceiling to be
-	    used if the chosen default priority inversion protocol is
-	    priority ceiling protocol. The default value for this is zero,
-	    making all such mutexes boost threads to the maximum priority."
-    }
-
     cdl_option CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DYNAMIC {
 	display        "Specify mutex priority inversion protocol at runtime"
 	default_value  1
--- a/packages/kernel/current/include/smp.hxx
+++ b/packages/kernel/current/include/smp.hxx
@@ -184,7 +184,7 @@ public:
 
     ~Cyg_SpinLock()
     {
-        CYG_ASSERT( !test(), "spinlock still claimed");
+//        CYG_ASSERT( !test(), "spinlock still claimed");
     };
     
     // Spin on the lock.
@@ -223,7 +223,9 @@ public:
     // we have it.
     void spin_intsave(CYG_INTERRUPT_STATE *state)
     {
-        HAL_DISABLE_INTERRUPTS(*state);
+        CYG_INTERRUPT_STATE s;
+        HAL_DISABLE_INTERRUPTS(s);
+        *state = s;
         spin();
     };
 
@@ -380,7 +382,9 @@ public:
     // we have it.
     void spin_intsave(CYG_INTERRUPT_STATE *state)
     {
-        HAL_DISABLE_INTERRUPTS(*state);
+        CYG_INTERRUPT_STATE s;
+        HAL_DISABLE_INTERRUPTS(s);
+        *state = s;
         spin();
     };
 
--- a/packages/kernel/current/src/common/kapi.cxx
+++ b/packages/kernel/current/src/common/kapi.cxx
@@ -1008,13 +1008,13 @@ externC cyg_bool_t cyg_spinlock_test( cy
 externC void cyg_spinlock_spin_intsave( cyg_spinlock_t *lock,
                                 cyg_addrword_t *istate )
 {
-    ((Cyg_SpinLock *)lock)->spin_intsave(istate);
+    ((Cyg_SpinLock *)lock)->spin_intsave((CYG_INTERRUPT_STATE *)istate);
 }
     
 externC void cyg_spinlock_clear_intsave( cyg_spinlock_t *lock,
                                  cyg_addrword_t istate )
 {
-    ((Cyg_SpinLock *)lock)->clear_intsave(istate);
+    ((Cyg_SpinLock *)lock)->clear_intsave((CYG_INTERRUPT_STATE)istate);
 }
     
 
new file mode 100644
--- /dev/null
+++ b/packages/kernel/current/tests/kmutex3.c
@@ -0,0 +1,630 @@
+//==========================================================================
+//
+//        kmutex3.c
+//
+//        Mutex test 3 - priority inheritance
+//
+//==========================================================================
+//####COPYRIGHTBEGIN####
+//                                                                          
+// -------------------------------------------                              
+// The contents of this file are subject to the Red Hat eCos Public License 
+// Version 1.1 (the "License"); you may not use this file except in         
+// compliance with the License.  You may obtain a copy of the License at    
+// http://www.redhat.com/                                                   
+//                                                                          
+// Software distributed under the License is distributed on an "AS IS"      
+// basis, WITHOUT WARRANTY OF ANY KIND, either express or implied.  See the 
+// License for the specific language governing rights and limitations under 
+// the License.                                                             
+//                                                                          
+// The Original Code is eCos - Embedded Configurable Operating System,      
+// released September 30, 1998.                                             
+//                                                                          
+// The Initial Developer of the Original Code is Red Hat.                   
+// Portions created by Red Hat are                                          
+// Copyright (C) 1998, 1999, 2000, 2001 Red Hat, Inc.
+// All Rights Reserved.                                                     
+// -------------------------------------------                              
+//                                                                          
+//####COPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):     hmt
+// Contributors:  hmt
+// Date:          2000-01-06, 2001-08-10
+// Description:   Tests mutex priority inheritance.  This is simply a
+//                translation of the similarly named kernel test to the
+//                KAPI, with the intention of also testing the new
+//                "set the protocol at run-time" extensions.
+//####DESCRIPTIONEND####
+
+#include <pkgconf/hal.h>
+#include <pkgconf/kernel.h>
+
+#include <cyg/infra/testcase.h>
+
+#include <cyg/hal/hal_arch.h>           // CYGNUM_HAL_STACK_SIZE_TYPICAL
+
+#include <cyg/infra/diag.h>             // diag_printf
+
+#ifdef CYGSEM_HAL_STOP_CONSTRUCTORS_ON_FLAG
+externC void
+cyg_hal_invoke_constructors();
+#endif
+
+// ------------------------------------------------------------------------
+//
+// These checks should be enough; any other scheduler which has priorities
+// should manifest as having no priority inheritance, but otherwise fine,
+// so the test should work correctly.
+
+#if defined(CYGVAR_KERNEL_COUNTERS_CLOCK) &&    \
+    (CYGNUM_KERNEL_SCHED_PRIORITIES > 20) &&    \
+    defined(CYGFUN_KERNEL_API_C) &&             \
+    !defined(CYGPKG_KERNEL_SMP_SUPPORT)
+
+
+#include <cyg/kernel/kapi.h>
+
+#include <cyg/infra/cyg_ass.h>
+#include <cyg/infra/cyg_trac.h>
+#include <cyg/infra/diag.h>             // diag_printf
+
+
+// ------------------------------------------------------------------------
+// manufacture a simpler feature test macro for priority inheritance than
+// the configuration gives us. We have priority inheritance if it is configured
+// as the only protocol, or if it is the default protocol for dynamic protocol
+// choice.
+// FIXME: If we have dynamic protocol choice, we can also set priority inheritance
+// as the protocol to be used on the mutexes we are interested in. At present we
+// do not do this.
+
+#ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_INHERIT
+# ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DYNAMIC
+#  ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_INHERIT
+#   define PRIORITY_INHERITANCE "dynamic-default-inherit"
+#  endif
+# else
+#  define PRIORITY_INHERITANCE "static-inherit"
+# endif
+#endif
+
+#ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_CEILING
+# ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DYNAMIC
+#  ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_CEILING
+#   if CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY <= 5
+#    define PRIORITY_INHERITANCE "dynamic-default-ceiling-high"
+#   elif CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY >= 15
+#    define NO_PRIORITY_INHERITANCE "dynamic-default-ceiling-low"
+#   else
+#    define PRIORITY_UNKNOWN "dynamic-default-ceiling-mid"
+#   endif
+#  endif
+# else
+#  if CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY <= 5
+#   define PRIORITY_INHERITANCE "static-ceiling-high"
+#  elif CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY >= 15
+#   define NO_PRIORITY_INHERITANCE "static-ceiling-low"
+#  else
+#   define PRIORITY_UNKNOWN "static-ceiling-mid"
+#  endif
+# endif
+#endif
+
+#ifndef PRIORITY_INHERITANCE
+# ifndef NO_PRIORITY_INHERITANCE
+#  define NO_PRIORITY_INHERITANCE "no scheme selected"
+# endif
+#endif
+
+// ------------------------------------------------------------------------
+// Management functions
+//
+// Stolen from testaux.hxx and copied in here because I want to be able to
+// reset the world also.
+//
+// Translated into KAPI also.
+
+#define NTHREADS 7
+
+#define STACKSIZE CYGNUM_HAL_STACK_SIZE_TYPICAL
+
+static  cyg_handle_t thread[NTHREADS] = { 0 };
+
+typedef cyg_uint64 CYG_ALIGNMENT_TYPE;
+
+static cyg_thread thread_obj[NTHREADS];
+
+static CYG_ALIGNMENT_TYPE stack[NTHREADS] [
+   (STACKSIZE+sizeof(CYG_ALIGNMENT_TYPE)-1)
+     / sizeof(CYG_ALIGNMENT_TYPE)                     ];
+
+static int nthreads = 0;
+
+#undef NULL
+#define NULL (0)
+
+static cyg_handle_t new_thread( cyg_thread_entry_t *entry,
+                                cyg_addrword_t data,
+                                cyg_addrword_t priority,
+                                int do_resume )
+{
+    CYG_ASSERT(nthreads < NTHREADS, 
+               "Attempt to create more than NTHREADS threads");
+
+    cyg_thread_create( priority,
+                       entry,
+                       data, 
+                       NULL,                // no name
+                       (void *)(stack[nthreads]),
+                       STACKSIZE,
+                       &thread[nthreads],
+                       &thread_obj[nthreads] );
+
+    if ( do_resume )
+        cyg_thread_resume( thread[nthreads] );
+
+    return thread[nthreads++];
+}
+
+
+static void kill_threads( void )
+{
+    CYG_ASSERT(nthreads <= NTHREADS, 
+               "More than NTHREADS threads");
+    CYG_ASSERT( cyg_thread_self() == thread[0],
+                "kill_threads() not called from thread 0");
+    while ( nthreads > 1 ) {
+        nthreads--;
+        if ( NULL != thread[nthreads] ) {
+            do
+                cyg_thread_kill( thread[nthreads] );
+            while ( ! cyg_thread_delete ( thread[nthreads] ) );
+            thread[nthreads] = NULL;
+        }
+    }
+    CYG_ASSERT(nthreads == 1,
+               "No threads left");
+}
+
+// ------------------------------------------------------------------------
+
+#define DELAYFACTOR 1 // for debugging
+
+// ------------------------------------------------------------------------
+
+static cyg_mutex_t mutex_obj;
+static cyg_mutex_t *mutex;
+
+// These are for reporting back to the master thread
+volatile int got_it  = 0;
+volatile int t3ran   = 0;
+volatile int t3ended = 0;
+volatile int extras[4] = {0,0,0,0};
+    
+volatile int go_flag = 0; // but this one controls thread 3 from thread 2
+
+// ------------------------------------------------------------------------
+// 0 to 3 of these run generally to interfere with the other processing,
+// to cause multiple prio inheritances, and clashes in any orders.
+
+static void extra_thread( cyg_addrword_t data )
+{
+    cyg_handle_t self = cyg_thread_self();
+
+#define XINFO( z ) \
+    do { z[13] = '0' + data; CYG_TEST_INFO( z ); } while ( 0 )
+
+    static char running[]  = "Extra thread Xa running";
+    static char exiting[]  = "Extra thread Xa exiting";
+    static char resumed[]  = "Extra thread Xa resumed";
+    static char locked[]   = "Extra thread Xa locked";
+    static char unlocked[] = "Extra thread Xa unlocked";
+
+    XINFO( running );
+
+    cyg_thread_suspend( self );
+
+    XINFO( resumed );
+
+    cyg_mutex_lock( mutex );
+
+    XINFO( locked );
+
+    cyg_mutex_unlock( mutex );
+
+    XINFO( unlocked );
+
+    extras[ data ] ++;
+
+    XINFO( exiting );
+
+}
+
+// ------------------------------------------------------------------------
+
+static void t1( cyg_addrword_t data )
+{
+    cyg_handle_t self = cyg_thread_self();
+
+    CYG_TEST_INFO( "Thread 1 running" );
+
+    cyg_thread_suspend( self );
+
+    cyg_mutex_lock( mutex );
+
+    got_it++;
+
+    CYG_TEST_CHECK( 0 == t3ended, "T3 ended prematurely [T1,1]" );
+
+    cyg_mutex_unlock( mutex );
+
+    CYG_TEST_CHECK( 0 == t3ended, "T3 ended prematurely [T1,2]" );
+
+    // That's all.
+
+    CYG_TEST_INFO( "Thread 1 exit" );
+}
+
+// ------------------------------------------------------------------------
+
+static void t2( cyg_addrword_t data )
+{
+    cyg_handle_t self = cyg_thread_self();
+    int i;
+    cyg_tick_count_t then, now;
+
+    CYG_TEST_INFO( "Thread 2 running" );
+
+    CYG_TEST_CHECK( 0 == (data & ~0x77), "Bad T2 arg: extra bits" );
+    CYG_TEST_CHECK( 0 == (data & (data >> 4)), "Bad T2 arg: overlap" );
+
+    cyg_thread_suspend( self );
+
+    // depending on our config argument, optionally restart some of the
+    // extra threads to throw noise into the scheduler:
+    for ( i = 0; i < 3; i++ )
+        if ( (1 << i) & data )          // bits 0-2 control
+            cyg_thread_resume( thread[i+4] ); // extras are thread[4-6]
+
+    cyg_thread_delay( DELAYFACTOR * 10 ); // let those threads run
+
+    cyg_scheduler_lock();               // do this next lot atomically
+
+    go_flag = 1;                        // unleash thread 3
+    cyg_thread_resume( thread[1] );     // resume thread 1
+
+    // depending on our config argument, optionally restart some of the
+    // extra threads to throw noise into the scheduler at this later point:
+    for ( i = 4; i < 7; i++ )
+        if ( (1 << i) & data )          // bits 4-6 control
+            cyg_thread_resume( thread[i] ); // extras are thread[4-6]
+
+    cyg_scheduler_unlock();             // let scheduling proceed
+
+    // Need a delay (but not a CPU yield) to allow t3 to awaken and act on
+    // the go_flag, otherwise we check these details below too soon.
+    // Actually, waiting for the clock to tick a couple of times would be
+    // better, so that is what we will do.  Must be a busy-wait.
+    then = cyg_current_time();
+    do {
+        now = cyg_current_time();
+        // Wait longer than the delay in t3 waiting on go_flag
+    } while ( now < (then + 3) );
+
+#ifdef PRIORITY_UNKNOWN
+    CYG_TEST_INFO( "Not checking: " PRIORITY_UNKNOWN );
+#else
+#ifdef PRIORITY_INHERITANCE
+    CYG_TEST_INFO( "Checking priority scheme: " PRIORITY_INHERITANCE );
+    CYG_TEST_CHECK( 1 == t3ran, "Thread 3 did not run" );
+    CYG_TEST_CHECK( 1 == got_it, "Thread 1 did not get the mutex" );
+#else
+    CYG_TEST_INFO( "Checking NO priority scheme: " NO_PRIORITY_INHERITANCE );
+    CYG_TEST_CHECK( 0 == t3ran, "Thread 3 DID run" );
+    CYG_TEST_CHECK( 0 == got_it, "Thread 1 DID get the mutex" );
+#endif
+#endif
+
+    CYG_TEST_CHECK( 0 == t3ended, "Thread 3 ended prematurely [T2,1]" );
+
+    cyg_thread_delay( DELAYFACTOR * 20 ); // let those threads run
+
+    CYG_TEST_CHECK( 1 == t3ran, "Thread 3 did not run" );
+    CYG_TEST_CHECK( 1 == got_it, "Thread 1 did not get the mutex" );
+    CYG_TEST_CHECK( 1 == t3ended, "Thread 3 has not ended" );
+
+    for ( i = 0; i < 3; i++ )
+        if ( (1 << i) & (data | data >> 4) ) // bits 0-2 and 4-6 control
+            CYG_TEST_CHECK( 1 == extras[i+1], "Extra thread did not run" );
+        else
+            CYG_TEST_CHECK( 0 == extras[i+1], "Extra thread ran" );
+
+    CYG_TEST_PASS( "Thread 2 exiting, AOK" );
+    // That's all: restart the control thread.
+    cyg_thread_resume( thread[0] );
+}
+
+// ------------------------------------------------------------------------
+
+static void t3( cyg_addrword_t data )
+{
+    CYG_TEST_INFO( "Thread 3 running" );
+
+    cyg_mutex_lock( mutex );
+
+    cyg_thread_delay( DELAYFACTOR * 5 ); // let thread 3a run
+
+    cyg_thread_resume( thread[2] );     // resume thread 2
+
+    while ( 0 == go_flag )
+        cyg_thread_delay(1);            // wait until we are told to go
+
+    t3ran ++;                           // record the fact
+
+    CYG_TEST_CHECK( 0 == got_it, "Thread 1 claims to have got my mutex" );
+    
+    cyg_mutex_unlock( mutex );
+    
+    t3ended ++;                         // record that we came back
+
+    CYG_TEST_CHECK( 1 == got_it, "Thread 1 did not get the mutex" );
+
+    CYG_TEST_INFO( "Thread 3 exit" );
+}
+
+// ------------------------------------------------------------------------
+
+static void control_thread( cyg_addrword_t data )
+{
+    cyg_handle_t self = cyg_thread_self();
+    int i, z;
+
+    CYG_TEST_INIT();
+    CYG_TEST_INFO( "Control Thread running" );
+
+    // Go through the 27 possibilitied of resuming the extra threads
+    //     0: not at all
+    //     1: early in the process
+    //     2: later on
+    // which are represented by bits 0-3 and 4-6 resp in the argument to
+    // thread 2 (none set means no resume at all).
+    for ( i = 0; i < 27; i++ ) {
+        static int xx[] = { 0, 1, 16 };
+        int j = i % 3;
+        int k = (i / 3) % 3;
+        int l = (i / 9) % 3;
+
+        int d = xx[j] | (xx[k]<<1) | (xx[l]<<2) ;
+
+        if ( cyg_test_is_simulator && (0 != i && 13 != i && 26 != i) )
+            continue;    // 13 is 111 base 3, 26 is 222 base 3
+
+#ifdef PRIORITY_INHERITANCE
+        // If the simple scheme plus relay enhancement, or any other
+        // *complete* scheme, we can run all three ancillary threads no
+        // problem, so no special action here.
+
+#else
+        // If no priority inheritance at all, running threads 1a and 2a is
+        // OK, but not thread 3a; it blocks the world.
+        if ( l )                        // Cannot run thread 3a if no
+            break;                      //     priority inheritance at all.
+#endif
+
+        mutex = &mutex_obj;
+        cyg_mutex_init( mutex );
+
+        got_it  = 0;
+        t3ran   = 0;
+        t3ended = 0;
+        for ( z = 0; z < 4; z++ ) extras[z] = 0;
+        go_flag = 0;
+        
+        new_thread( t1, 0,  5, 1 );            // Slot 1
+        new_thread( t2, d, 10, 1 );            // Slot 2
+        new_thread( t3, 0, 15, 1 );            // Slot 3
+        
+        new_thread( extra_thread, 1,  8, j );  // Slot 4
+        new_thread( extra_thread, 2, 12, k );  // Slot 5
+        new_thread( extra_thread, 3, 17, l );  // Slot 6
+        
+        {
+            static char *a[] = { "inactive", "run early", "run late" };
+            diag_printf( "\n----- [%2d] New Cycle: 0x%02x, Threads 1a %s, 2a %s, 3a %s -----\n",
+                         i, d,  a[j], a[k], a[l] );
+        }
+
+        cyg_thread_suspend( self );
+        
+        kill_threads();
+        cyg_mutex_destroy( mutex );
+    }
+    CYG_TEST_EXIT( "Control Thread exit" );
+}
+
+// ------------------------------------------------------------------------
+
+externC void
+cyg_user_start( void )
+{ 
+#ifdef CYGSEM_HAL_STOP_CONSTRUCTORS_ON_FLAG
+    cyg_hal_invoke_constructors();
+#endif
+    new_thread( control_thread, 0, 2, 1 );
+}
+
+#else // CYGVAR_KERNEL_COUNTERS_CLOCK &c
+
+externC void
+cyg_start( void )
+{
+    CYG_TEST_INIT();
+    CYG_TEST_PASS_FINISH("KMutex3 test requires:\n"
+                         "CYGFUN_KERNEL_API_C &&\n"
+                         "CYGVAR_KERNEL_COUNTERS_CLOCK &&\n"
+                         "(CYGNUM_KERNEL_SCHED_PRIORITIES > 20) &&\n"
+                         "!defined(CYGPKG_KERNEL_SMP_SUPPORT)\n");
+}
+#endif // CYGVAR_KERNEL_COUNTERS_CLOCK &c
+
+
+// ------------------------------------------------------------------------
+// Documentation: enclosed is the design of this test.
+//
+// It has been carefully constructed so that it does NOT use other kernel
+// facilities (aside from delay-task) to test that priority inheritance is
+// working, or not, as intended by the configuration.
+//
+// These notes describe the flow of control in one run of the test with the
+// ancillary tasks optionally interspersed.  The details of how those extra
+// tasks are or are not allowed to run are not described.
+// 
+// 
+// 
+// The only change in the test that depends on whether there is inheritance or
+// not is the check in thread 2 on "3-ran" and "got it" flags marked ****
+// 
+// 
+// volatile &c booleans:
+//         "got it"     = FALSE
+//         "3-ran"      = FALSE
+//         "3-ended"    = FALSE
+//         "extras"[3]  = FALSE
+// 
+// thread 1.  prio 5, self-suspend.
+// 
+// thread 1a, prio 8, self-suspend.
+// 
+// thread 2.  prio 10, self-suspend.
+// 
+// thread 2a, prio 12, self-suspend.
+// 
+// thread 3.  prio 15, runs, lock mutex, resume(2)
+// 
+// thread 3a, prio 17, self-suspend.
+// 
+//        2.  runs,
+//        2.  resume(3a) +++OPTIONAL
+//        2.  resume(2a) +++OPTIONAL
+//        2.  resume(1a) +++OPTIONAL
+//        [1a lock-fail]	thread 3->prio := 8
+// 
+//        [3. runs maybe, does the looping thing]
+// 
+//        2.  sleep a while...
+// 
+//        [2a lock-fail]	thread 3->prio := 12
+// 
+//        [3. runs maybe, does the looping thing]
+// 
+//        [3a lock-fail]   thread 3->prio unchanged
+// 
+//        [3. runs maybe, does the looping thing]
+// 
+//        2.  lock scheduler
+//        2.  set "go-flag"
+//        2.  resume(1)
+//        2.  resume(1a) +++OPTIONAL
+//        2.  resume(2a) +++OPTIONAL
+//        2.  resume(3a) +++OPTIONAL
+//        2.  unlock scheduler
+// 
+//        1.  runs, lock mutex - thread 3 has it locked
+//
+//        2.  busy-waits a bit for thread 3 to come out of its delay() loop.
+//            This must be a *busy*wait so that 3 can only run via the
+//            inherited raised priority.
+// 
+//        [xa. all do the same: lock mutex,                ]
+//        [xa. unlock mutex                                ]
+//        [xa. set a flag "extras"[x] to say we are done.  ]
+//        [xa. exit                                        ]
+// 
+// 
+// 
+// INHERIT
+// -------
+// 
+//                 thread 3->prio := 5
+// 
+//        3.  runs,
+//        3.  set a flag to say "3-ran",
+//        3.  loop with a sleep(1) until "go-flag" is set.
+//        3.  check "got it" is false,
+//        3.  then unlock mutex,
+// 
+//                 thread 3->prio := 15
+// 
+//        1.  runs, set a flag to say "got it",
+//        1.  check "3-ended" flag is false
+//        1.  unlock mutex,
+//        1.  check "3-ended" flag is still false
+//        1.  exit.
+// 
+//        [1a locks, unlocks, exits]
+// 
+//        2.  runs, check "3-ran" and "got it" flags are TRUE ****
+//        2.  check "3-ended" flag is false
+//        2.  sleeps for a while so that...
+// 
+//        [2a locks, unlocks, exits]
+//            
+//        3.  runs, set "3-ended" flag,
+//        3.  check "3-ran" and "got it" flags
+//        3.  exit
+// 
+//        [3a locks, unlocks, exits]
+// 
+//        2.  awakens, checks all flags true,
+//        2.  check that all "extra" threads that we started have indeed run
+//        2.  end of test.
+// 
+// 
+// 
+// 
+// NO-INHERIT
+// ----------
+//                 thread 1 is waiting on the mutex
+// 
+//        [1a lock-fail]
+// 
+//        2.  runs, checks that "3-ran" and "got it" flags are FALSE ****
+//        2.  check "3-ended" flag is false
+//        2.  sleeps for a while so that...
+// 
+//        [2a. lock-fail]
+//            
+//        3.  runs, set a flag to say "3-ran",
+//        3.  check "got it" is false,
+//        3.  then unlock mutex,
+// 
+//        1.  runs, set a flag to say "got it",
+//        1.  check "3-ended" flag is false
+//        1.  unlock mutex,
+//        1.  check "3-ended" flag is still false
+//        1.  exit.
+// 
+//        [1a locks, unlocks, exits]
+//        [2a locks, unlocks, exits]
+// 
+//        3.  runs, set "3-ended" flag,
+//        3.  check "3-ran" and "got it" flags
+//        3.  exit
+// 
+//        [3a locks, unlocks, exits]
+//                
+//        2.  awakens, checks all flags true, 
+//        2.  check that all "extra" threads that we started have indeed run
+//        2.  end of test.
+// 
+// 
+// (the end)
+// 
+// 
+// ------------------------------------------------------------------------
+
+// EOF mutex3.cxx
--- a/packages/kernel/current/tests/mutex3.cxx
+++ b/packages/kernel/current/tests/mutex3.cxx
@@ -79,15 +79,39 @@ cyg_hal_invoke_constructors();
 #ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_INHERIT
 # ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DYNAMIC
 #  ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_INHERIT
-#   define PRIORITY_INHERITANCE
-#  else
-#   undef PRIORITY_INHERITANCE
+#   define PRIORITY_INHERITANCE "dynamic-default-inherit"
 #  endif
 # else
-#  define PRIORITY_INHERITANCE
+#  define PRIORITY_INHERITANCE "static-inherit"
 # endif
-#else
-# undef PRIORITY_INHERITANCE
+#endif
+
+#ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_CEILING
+# ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DYNAMIC
+#  ifdef CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_CEILING
+#   if CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY <= 5
+#    define PRIORITY_INHERITANCE "dynamic-default-ceiling-high"
+#   elif CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY >= 15
+#    define NO_PRIORITY_INHERITANCE "dynamic-default-ceiling-low"
+#   else
+#    define PRIORITY_UNKNOWN "dynamic-default-ceiling-mid"
+#   endif
+#  endif
+# else
+#  if CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY <= 5
+#   define PRIORITY_INHERITANCE "static-ceiling-high"
+#  elif CYGSEM_KERNEL_SYNCH_MUTEX_PRIORITY_INVERSION_PROTOCOL_DEFAULT_PRIORITY >= 15
+#   define NO_PRIORITY_INHERITANCE "static-ceiling-low"
+#  else
+#   define PRIORITY_UNKNOWN "static-ceiling-mid"
+#  endif
+# endif
+#endif
+
+#ifndef PRIORITY_INHERITANCE
+# ifndef NO_PRIORITY_INHERITANCE
+#  define NO_PRIORITY_INHERITANCE "no scheme selected"
+# endif
 #endif
 
 // ------------------------------------------------------------------------
@@ -280,15 +304,19 @@ static void t2( CYG_ADDRWORD data )
         // Wait longer than the delay in t3 waiting on go_flag
     } while ( now < (then + 3) );
 
+#ifdef PRIORITY_UNKNOWN
+    CYG_TEST_INFO( "Not checking: " PRIORITY_UNKNOWN );
+#else
 #ifdef PRIORITY_INHERITANCE
-    CYG_TEST_INFO( "Checking for mutex priority inheritance" );
+    CYG_TEST_INFO( "Checking priority scheme: " PRIORITY_INHERITANCE );
     CYG_TEST_CHECK( 1 == t3ran, "Thread 3 did not run" );
     CYG_TEST_CHECK( 1 == got_it, "Thread 1 did not get the mutex" );
 #else
-    CYG_TEST_INFO( "Checking for NO mutex priority inheritance" );
+    CYG_TEST_INFO( "Checking NO priority scheme: " NO_PRIORITY_INHERITANCE );
     CYG_TEST_CHECK( 0 == t3ran, "Thread 3 DID run" );
     CYG_TEST_CHECK( 0 == got_it, "Thread 1 DID get the mutex" );
 #endif
+#endif
 
     CYG_TEST_CHECK( 0 == t3ended, "Thread 3 ended prematurely [T2,1]" );
 
--- a/packages/net/snmp/agent/current/ChangeLog
+++ b/packages/net/snmp/agent/current/ChangeLog
@@ -1,3 +1,8 @@
+2001-08-14  Gary Thomas  <gthomas@redhat.com>
+
+	* tests/snmpping.c: 
+	* cdl/snmpagent.cdl: Add CDL options to configure tests.
+
 2001-07-31  Hugo Tyson <hmt@redhat.com>
 2001-07-31  Ron Kundla <rkundla@nband.com>
 
--- a/packages/net/snmp/agent/current/cdl/snmpagent.cdl
+++ b/packages/net/snmp/agent/current/cdl/snmpagent.cdl
@@ -276,7 +276,7 @@ cdl_package CYGPKG_SNMPAGENT {
                 the set of global flags if present."
         }
 
-        cdl_option CYGPKG_SNMPAGENT_TESTS {
+        cdl_component CYGPKG_SNMPAGENT_TESTS {
             display "SNMP agent tests"
             flavor  data
             no_define
@@ -285,6 +285,34 @@ cdl_package CYGPKG_SNMPAGENT {
             }
             description   "
                 This option specifies the set of tests for the eCos SMNP agent."
+
+            cdl_option CYGSEM_SNMPAGENT_TESTS_PROMISCUOUS {
+                display "Run SNMP agent tests in promiscuous mode"
+                flavor  bool
+                default_value 0
+                description   "
+                    This option controls the tests for the eCos SMNP agent.
+                    Enabling it will enable promiscuous mode on the hardware
+                    interface."
+            }
+
+            cdl_option CYGSEM_SNMPAGENT_TESTS_SNMPv3 {
+                display "SNMP agent test for SNMP version 3"
+                flavor  bool
+                default_value 1
+                description   "
+                    This option controls the tests for the eCos SMNP agent.
+                    Enabling it will include setup and testing of SNMP v3 interfaces."
+            }
+
+            cdl_option CYGNUM_SNMPAGENT_TESTS_ITERATIONS {
+                display "Number of test iterations for SNMP agent test"
+                flavor  data	
+                default_value 1
+                description   "
+                    This option controls the number of times the basic test will
+                    be run for testing the eCos SMNP agent."
+            }
         }
     }
 }
--- a/packages/net/snmp/agent/current/tests/snmpping.c
+++ b/packages/net/snmp/agent/current/tests/snmpping.c
@@ -22,7 +22,7 @@
 //                                                                          
 // The Initial Developer of the Original Code is Red Hat.                   
 // Portions created by Red Hat are                                          
-// Copyright (C) 1998, 1999, 2000 Red Hat, Inc.                             
+// Copyright (C) 1998, 1999, 2000, 2001 Red Hat, Inc.                             
 // All Rights Reserved.                                                     
 // -------------------------------------------                              
 //                                                                          
@@ -105,7 +105,7 @@ CONNECTION WITH THE USE OR PERFORMANCE O
 //                                                                          
 // The Initial Developer of the Original Code is Red Hat.                   
 // Portions created by Red Hat are                                          
-// Copyright (C) 1998, 1999, 2000 Red Hat, Inc.                             
+// Copyright (C) 1998, 1999, 2000, 2001 Red Hat, Inc.                             
 // All Rights Reserved.                                                     
 // -------------------------------------------                              
 //                                                                          
@@ -135,9 +135,8 @@ CONNECTION WITH THE USE OR PERFORMANCE O
 //==========================================================================
 
 
-
 // -------------------------------------------------------------------------
-// Configuration of the test...
+// Configuration of the test... now from CDL
 
 // Do we test the interfaces in promiscuous mode?
 //#define PROMISC_TEST
@@ -146,7 +145,7 @@ CONNECTION WITH THE USE OR PERFORMANCE O
 //#define RUN_FOREVER
 
 // Do we initialize SNMP v3 MIBs and authentication database?
-#define TEST_SNMPv3
+//#define TEST_SNMPv3
 
 // ------------------------------------------------------------------------
 
@@ -157,9 +156,10 @@ CONNECTION WITH THE USE OR PERFORMANCE O
 
 #include <pkgconf/system.h>
 #include <pkgconf/net.h>
+#include <pkgconf/snmpagent.h>
 
 
-#ifdef  TEST_SNMPv3
+#ifdef  CYGSEM_SNMPAGENT_TEST_SNMPv3
 #include <ucd-snmp/config.h>
 #include <ucd-snmp/asn1.h>
 #include <ucd-snmp/snmp_api.h>
@@ -169,7 +169,7 @@ CONNECTION WITH THE USE OR PERFORMANCE O
 #include <ucd-snmp/usmUser.h>
 #include <ucd-snmp/usmStats.h>
 #include <ucd-snmp/snmpEngine.h>
-#endif // TEST_SNMPv3
+#endif // CYGSEM_SNMPAGENT_TEST_SNMPv3
 
 #include <cyg/infra/testcase.h>
 
@@ -409,7 +409,7 @@ ping_test_loopback( int lo )
     close(s);
 }
 
-#ifdef PROMISC_TEST
+#ifdef CYGSEM_SNMPAGENT_TESTS_PROMISCUOUS
 static void 
 interface_promisc(const char *intf)
 {
@@ -429,21 +429,18 @@ interface_promisc(const char *intf)
   }
   close(s);
 }
-#endif // PROMISC_TEST
+#endif // CYGSEM_SNMPAGENT_TESTS_PROMISCUOUS
 
 void
 net_test(cyg_addrword_t p)
 {
-#ifdef RUN_FOREVER
-    int i = 9999999;
-#else
-    int i = 1;
-#endif
+    int i = CYGNUM_SNMPAGENT_TESTS_ITERATIONS;
     int j;
+
     diag_printf("Start PING test\n");
     TNR_INIT();
     init_all_network_interfaces();
-#ifdef PROMISC_TEST
+#ifdef CYGSEM_SNMPAGENT_TESTS_PROMISCUOUS
 #ifdef CYGHWR_NET_DRIVER_ETH0
         if (eth0_up)
             interface_promisc("eth0");
@@ -452,17 +449,17 @@ net_test(cyg_addrword_t p)
         if (eth1_up)
             interface_promisc("eth1");
 #endif
-#endif // PROMISC_TEST
+#endif // CYGSEM_SNMPAGENT_TESTS_PROMISCUOUS
 #ifdef CYGPKG_SNMPAGENT
     {
         extern void cyg_net_snmp_init(void);
         cyg_net_snmp_init();
-#ifdef  TEST_SNMPv3
+#ifdef  CYGSEM_SNMPAGENT_TEST_SNMPv3
         init_usmUser();             /* MIBs to support SNMPv3             */
         init_usmStats();
         init_snmpEngine();
         usm_parse_create_usmUser(NULL, "root MD5 md5passwd DES DESpasswd");
-#endif //  TEST_SNMPv3
+#endif //  CYGSEM_SNMPAGENT_TEST_SNMPv3
     }
 #endif // CYGPKG_SNMPAGENT
     do {
--- a/packages/redboot/current/ChangeLog
+++ b/packages/redboot/current/ChangeLog
@@ -1,3 +1,7 @@
+2001-08-14  Jonathan Larmour  <jlarmour@redhat.com>
+
+	* src/io.c (gets): Allow $'s and +'s to be escaped.
+
 2001-08-10  Jesper Skov  <jskov@redhat.com>
 
 	* src/flash.c (do_flash_init): Print error message instead of
--- a/packages/redboot/current/src/io.c
+++ b/packages/redboot/current/src/io.c
@@ -305,16 +305,24 @@ gets(char *buf, int buflen, int timeout)
             }
             break;
 #ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
-        case '+':
-            // If start of line, treat as GDB protocol. Otherwise fall
-            // through to default.
-            if (ptr == buf)
+        case '\\':                 // escape character
+            if (console_echo) {
+                mon_write_char(c);
+            }
+            if (last_ch != '\\') // if last was also an escape, 
+                break;             // don't add to buffer, just move on
+            *ptr++ = c;
+            c = '\0';    // cheat so that the "shift" state resets
+            break;
+        case '+': // fall through
         case '$':
+            if (ptr == buf || last_ch != '\\')
             {
                 // Give up and try GDB protocol
                 ungetDebugChar(c);  // Push back character so stubs will see it
                 return _GETS_GDB;
             }
+            // else fall through
 #endif
         default:
             if (console_echo) {