--- /tmp/linux-2.2.10/arch/i386/kernel/irq.c Tue Jul 13 00:33:09 1999 +++ linux-2.2.10/arch/i386/kernel/irq.c Thu Jul 15 18:21:23 1999 @@ -449,6 +449,7 @@ atomic_t global_bh_count; atomic_t global_bh_lock; +spinlock_t i386_bh_lock = SPIN_LOCK_UNLOCKED; /* * "global_cli()" is a special case, in that it can hold the --- /tmp/linux-2.2.10/include/asm-i386/softirq.h Sat Jan 23 17:28:57 1999 +++ linux-2.2.10/include/asm-i386/softirq.h Fri Jul 16 17:20:43 1999 @@ -9,25 +9,6 @@ #define get_active_bhs() (bh_mask & bh_active) #define clear_active_bhs(x) atomic_clear_mask((x),&bh_active) -extern inline void init_bh(int nr, void (*routine)(void)) -{ - bh_base[nr] = routine; - atomic_set(&bh_mask_count[nr], 0); - bh_mask |= 1 << nr; -} - -extern inline void remove_bh(int nr) -{ - bh_mask &= ~(1 << nr); - mb(); - bh_base[nr] = NULL; -} - -extern inline void mark_bh(int nr) -{ - set_bit(nr, &bh_active); -} - #ifdef __SMP__ /* @@ -37,6 +18,7 @@ */ extern atomic_t global_bh_lock; extern atomic_t global_bh_count; +extern spinlock_t i386_bh_lock; extern void synchronize_bh(void); @@ -91,21 +73,58 @@ #endif /* SMP */ +extern inline void init_bh(int nr, void (*routine)(void)) +{ + unsigned long flags; + + bh_base[nr] = routine; + atomic_set(&bh_mask_count[nr], 0); + + spin_lock_irqsave(&i386_bh_lock, flags); + bh_mask |= 1 << nr; + spin_unlock_irqrestore(&i386_bh_lock, flags); +} + +extern inline void remove_bh(int nr) +{ + unsigned long flags; + + spin_lock_irqsave(&i386_bh_lock, flags); + bh_mask &= ~(1 << nr); + spin_unlock_irqrestore(&i386_bh_lock, flags); + + synchronize_bh(); + bh_base[nr] = NULL; +} + +extern inline void mark_bh(int nr) +{ + set_bit(nr, &bh_active); +} + /* * These use a mask count to correctly handle * nested disable/enable calls */ extern inline void disable_bh(int nr) { + unsigned long flags; + + spin_lock_irqsave(&i386_bh_lock, flags); bh_mask &= ~(1 << nr); atomic_inc(&bh_mask_count[nr]); + spin_unlock_irqrestore(&i386_bh_lock, flags); synchronize_bh(); } extern inline void enable_bh(int nr) { + unsigned long flags; + + spin_lock_irqsave(&i386_bh_lock, flags); if (atomic_dec_and_test(&bh_mask_count[nr])) bh_mask |= 1 << nr; + spin_unlock_irqrestore(&i386_bh_lock, flags); } #endif /* __ASM_SOFTIRQ_H */ --- /tmp/linux-2.2.10/arch/i386/kernel/i386_ksyms.c Tue Jul 13 00:33:09 1999 +++ linux-2.2.10/arch/i386/kernel/i386_ksyms.c Fri Jul 16 17:16:29 1999 @@ -88,6 +88,7 @@ EXPORT_SYMBOL(global_bh_count); EXPORT_SYMBOL(global_bh_lock); EXPORT_SYMBOL(global_irq_holder); +EXPORT_SYMBOL(i386_bh_lock); EXPORT_SYMBOL(__global_cli); EXPORT_SYMBOL(__global_sti); EXPORT_SYMBOL(__global_save_flags);