diff -urNX dontdiff linux-2.5.22/arch/cris/drivers/serial.c linux-2.5.22-bh/arch/cris/drivers/serial.c
--- linux-2.5.22/arch/cris/drivers/serial.c     Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/arch/cris/drivers/serial.c  Mon Jun 17 13:04:29 2002
@@ -333,8 +333,6 @@

#define _INLINE_ inline

-static DECLARE_TASK_QUEUE(tq_serial);
-
struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -1092,8 +1090,7 @@
                                   int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

/* The output DMA channel is free - use it to send as many chars as possible
@@ -1955,12 +1952,6 @@
 * them using rs_sched_event(), and they get done here.
 */
static void
-do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
-static void
do_softint(void *private_)
{
       struct e100_serial      *info = (struct e100_serial *) private_;
@@ -3483,8 +3474,6 @@

       show_serial_version();

-       init_bh(SERIAL_BH, do_serial_bh);
-
       /* Setup the timed flush handler system */

#if !defined(CONFIG_ETRAX_SERIAL_FAST_TIMER) && !defined(CONFIG_ETRAX_SERIAL_FLUSH_DMA_FAST)
diff -urNX dontdiff linux-2.5.22/arch/cris/drivers/usb-host.c linux-2.5.22-bh/arch/cris/drivers/usb-host.c
--- linux-2.5.22/arch/cris/drivers/usb-host.c   Sun Jun  2 18:44:46 2002
+++ linux-2.5.22-bh/arch/cris/drivers/usb-host.c        Mon Jun 17 12:28:20 2002
@@ -1972,8 +1972,7 @@
       reg->usb_bh.routine = etrax_usb_hc_intr_bottom_half;
       reg->usb_bh.data = reg;

-       queue_task(&reg->usb_bh, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&reg->usb_bh);

       DBFEXIT;
}
diff -urNX dontdiff linux-2.5.22/arch/mips/au1000/common/serial.c linux-2.5.22-bh/arch/mips/au1000/common/serial.c
--- linux-2.5.22/arch/mips/au1000/common/serial.c       Sun Jun  2 18:44:46 2002
+++ linux-2.5.22-bh/arch/mips/au1000/common/serial.c    Mon Jun 17 13:04:50 2002
@@ -124,8 +124,6 @@

static char *serial_name = "Serial driver";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -331,8 +329,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(struct async_struct *info,
@@ -621,11 +618,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct async_struct     *info = (struct async_struct *) private_;
@@ -2560,7 +2552,6 @@
       int i;
       struct serial_state * state;

-       init_bh(SERIAL_BH, do_serial_bh);
       init_timer(&serial_timer);
       serial_timer.function = rs_timer;
       mod_timer(&serial_timer, jiffies + RS_STROBE_TIME);
@@ -2818,7 +2809,6 @@
       /* printk("Unloading %s: version %s\n", serial_name, serial_version); */
       del_timer_sync(&serial_timer);
       save_flags(flags); cli();
-        remove_bh(SERIAL_BH);
       if ((e1 = tty_unregister_driver(&serial_driver)))
               printk("serial: failed to unregister serial driver (%d)\n",
                      e1);
diff -urNX dontdiff linux-2.5.22/arch/mips/baget/vacserial.c linux-2.5.22-bh/arch/mips/baget/vacserial.c
--- linux-2.5.22/arch/mips/baget/vacserial.c    Sun Jun  2 18:44:51 2002
+++ linux-2.5.22-bh/arch/mips/baget/vacserial.c Mon Jun 17 13:04:39 2002
@@ -93,8 +93,6 @@
static char *serial_name = "VAC Serial driver";
static char *serial_version = "4.26";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -323,8 +321,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(struct async_struct *info,
@@ -586,11 +583,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct async_struct     *info = (struct async_struct *) private_;
@@ -2321,7 +2313,6 @@
       dualsp_serial_init ();
#endif

-       init_bh(SERIAL_BH, do_serial_bh);
       init_timer(&vacs_timer);
       vacs_timer.function = rs_timer;
       vacs_timer.expires = 0;
@@ -2529,7 +2520,6 @@
       cli();

       del_timer_sync(&vacs_timer);
-        remove_bh(SERIAL_BH);

       if ((e1 = tty_unregister_driver(&serial_driver)))
               printk("SERIAL: failed to unregister serial driver (%d)\n",
diff -urNX dontdiff linux-2.5.22/arch/mips/gt64120/common/gt_irq.c linux-2.5.22-bh/arch/mips/gt64120/common/gt_irq.c
--- linux-2.5.22/arch/mips/gt64120/common/gt_irq.c      Sun Jun  2 18:44:52 2002
+++ linux-2.5.22-bh/arch/mips/gt64120/common/gt_irq.c   Mon Jun 17 12:29:42 2002
@@ -134,10 +134,8 @@
                       if (irq_src & (1 << count)) {
                               if (irq_handlers[INT_CAUSE_MAIN][count].
                                   routine) {
-                                       queue_task(&irq_handlers
-                                                  [INT_CAUSE_MAIN][count],
-                                                  &tq_immediate);
-                                       mark_bh(IMMEDIATE_BH);
+                                       queue_immediate_task(&irq_handlers
+                                                  [INT_CAUSE_MAIN][count]);
                                       handled = 1;
                               }
                       }
diff -urNX dontdiff linux-2.5.22/arch/ppc/8260_io/uart.c linux-2.5.22-bh/arch/ppc/8260_io/uart.c
--- linux-2.5.22/arch/ppc/8260_io/uart.c        Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/arch/ppc/8260_io/uart.c     Mon Jun 17 13:04:02 2002
@@ -74,8 +74,6 @@
static char *serial_name = "CPM UART driver";
static char *serial_version = "0.01";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;
static int serial_console_setup(struct console *co, char *options);
@@ -334,8 +332,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(ser_info_t *info)
@@ -631,11 +628,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       ser_info_t      *info = (ser_info_t *) private_;
@@ -2506,8 +2498,6 @@
       volatile        immap_t         *immap;
       volatile        iop8260_t       *io;

-       init_bh(SERIAL_BH, do_serial_bh);
-
       show_serial_version();

       /* Initialize the tty_driver structure */
diff -urNX dontdiff linux-2.5.22/arch/ppc/8xx_io/uart.c linux-2.5.22-bh/arch/ppc/8xx_io/uart.c
--- linux-2.5.22/arch/ppc/8xx_io/uart.c Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/arch/ppc/8xx_io/uart.c      Mon Jun 17 13:04:13 2002
@@ -86,8 +86,6 @@
static char *serial_name = "CPM UART driver";
static char *serial_version = "0.03";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;
static int serial_console_setup(struct console *co, char *options);
@@ -351,8 +349,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(ser_info_t *info, struct pt_regs *regs)
@@ -695,11 +692,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       ser_info_t      *info = (ser_info_t *) private_;
@@ -2555,8 +2547,6 @@
       volatile        scc_uart_t      *sup;
       volatile        immap_t         *immap;

-       init_bh(SERIAL_BH, do_serial_bh);
-
       show_serial_version();

       /* Initialize the tty_driver structure */
diff -urNX dontdiff linux-2.5.22/drivers/acorn/block/fd1772.c linux-2.5.22-bh/drivers/acorn/block/fd1772.c
--- linux-2.5.22/drivers/acorn/block/fd1772.c   Mon Jun 17 04:49:03 2002
+++ linux-2.5.22-bh/drivers/acorn/block/fd1772.c        Mon Jun 17 12:05:07 2002
@@ -1288,8 +1288,7 @@
               floppy_irqconsequencehandler();
       if ((MultReadInProgress) && (fdc1772_bytestogo==0)) fd_readtrack_check(0);
       if (fdc_busy) {
-               queue_task(&fd1772_tq,&tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&fd1772_tq);
       }
}

@@ -1311,8 +1310,7 @@

       redo_fd_request();

-       queue_task(&fd1772_tq,&tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&fd1772_tq);
}


diff -urNX dontdiff linux-2.5.22/drivers/acorn/block/mfmhd.c linux-2.5.22-bh/drivers/acorn/block/mfmhd.c
--- linux-2.5.22/drivers/acorn/block/mfmhd.c    Mon Jun 17 04:49:03 2002
+++ linux-2.5.22-bh/drivers/acorn/block/mfmhd.c Mon Jun 17 12:04:38 2002
@@ -866,8 +866,7 @@
       errors = &(CURRENT->errors);
#if 0
       mfm_tq.routine = (void (*)(void *)) mfm_initialise;
-       queue_task(&mfm_tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&mfm_tq);
#else
       mfm_initialise();
#endif
diff -urNX dontdiff linux-2.5.22/drivers/atm/ambassador.c linux-2.5.22-bh/drivers/atm/ambassador.c
--- linux-2.5.22/drivers/atm/ambassador.c       Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/atm/ambassador.c    Mon Jun 17 12:26:53 2002
@@ -926,8 +926,7 @@

    if (irq_work) {
#ifdef FILL_RX_POOLS_IN_BH
-      queue_task (&dev->bh, &tq_immediate);
-      mark_bh (IMMEDIATE_BH);
+      queue_immediate_task (&dev->bh);
#else
      fill_rx_pools (dev);
#endif
diff -urNX dontdiff linux-2.5.22/drivers/atm/idt77252.c linux-2.5.22-bh/drivers/atm/idt77252.c
--- linux-2.5.22/drivers/atm/idt77252.c Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/atm/idt77252.c      Mon Jun 17 12:27:24 2002
@@ -2896,8 +2896,7 @@
               if (stat & SAR_STAT_FBQ3A)
                       card->irqstat[8]++;

-               queue_task(&card->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&card->tqueue);
       }

out:
diff -urNX dontdiff linux-2.5.22/drivers/block/floppy.c linux-2.5.22-bh/drivers/block/floppy.c
--- linux-2.5.22/drivers/block/floppy.c Mon Jun 17 04:49:04 2002
+++ linux-2.5.22-bh/drivers/block/floppy.c      Mon Jun 17 12:26:30 2002
@@ -1001,8 +1001,7 @@
static void schedule_bh( void (*handler)(void*) )
{
       floppy_tq.routine = (void *)(void *) handler;
-       queue_task(&floppy_tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&floppy_tq);
}

static struct timer_list fd_timer;
diff -urNX dontdiff linux-2.5.22/drivers/cdrom/cm206.c linux-2.5.22-bh/drivers/cdrom/cm206.c
--- linux-2.5.22/drivers/cdrom/cm206.c  Mon Jun 17 04:49:04 2002
+++ linux-2.5.22-bh/drivers/cdrom/cm206.c       Mon Jun 17 05:42:50 2002
@@ -345,6 +345,8 @@
       }
}

+static struct tasklet_struct cm206_tasklet;
+
/* The interrupt handler. When the cm260 generates an interrupt, very
   much care has to be taken in reading out the registers in the right
   order; in case of a receive_buffer_full interrupt, first the
@@ -432,7 +434,7 @@
       if (cd->background
           && (cd->adapter_last - cd->adapter_first == cd->max_sectors
               || cd->fifo_overflowed))
-               mark_bh(CM206_BH);      /* issue a stop read command */
+               tasklet_schedule(&cm206_tasklet);       /* issue a stop read command */
       stats(interrupt);
}

@@ -701,7 +703,7 @@
   4 c_stop waits for receive_buffer_full: 0xff
*/

-void cm206_bh(void)
+static void cm206_tasklet_func(unsigned long ignore)
{
       debug(("bh: %d\n", cd->background));
       switch (cd->background) {
@@ -745,6 +747,8 @@
       }
}

+static DECLARE_TASKLET(cm206_tasklet, cm206_tasklet_func, 0);
+
/* This command clears the dsb_possible_media_change flag, so we must
 * retain it.
 */
@@ -1503,7 +1507,6 @@
       blk_init_queue(BLK_DEFAULT_QUEUE(MAJOR_NR), do_cm206_request,
                      &cm206_lock);
       blk_queue_hardsect_size(BLK_DEFAULT_QUEUE(MAJOR_NR), 2048);
-       init_bh(CM206_BH, cm206_bh);

       memset(cd, 0, sizeof(*cd));     /* give'm some reasonable value */
       cd->sector_last = -1;   /* flag no data buffered */
diff -urNX dontdiff linux-2.5.22/drivers/char/amiserial.c linux-2.5.22-bh/drivers/char/amiserial.c
--- linux-2.5.22/drivers/char/amiserial.c       Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/char/amiserial.c    Mon Jun 17 13:02:51 2002
@@ -102,8 +102,6 @@

static char *serial_name = "Amiga-builtin serial driver";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -276,8 +274,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(struct async_struct *info)
@@ -560,11 +557,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct async_struct     *info = (struct async_struct *) private_;
@@ -2118,8 +2110,6 @@
       if (!request_mem_region(CUSTOM_PHYSADDR+0x30, 4, "amiserial [Paula]"))
               return -EBUSY;

-       init_bh(SERIAL_BH, do_serial_bh);
-
       IRQ_ports = NULL;

       show_serial_version();
@@ -2243,7 +2233,6 @@
       /* printk("Unloading %s: version %s\n", serial_name, serial_version); */
       save_flags(flags);
       cli();
-        remove_bh(SERIAL_BH);
       if ((e1 = tty_unregister_driver(&serial_driver)))
               printk("SERIAL: failed to unregister serial driver (%d)\n",
                      e1);
diff -urNX dontdiff linux-2.5.22/drivers/char/cyclades.c linux-2.5.22-bh/drivers/char/cyclades.c
--- linux-2.5.22/drivers/char/cyclades.c        Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/drivers/char/cyclades.c     Mon Jun 17 13:01:32 2002
@@ -712,8 +712,6 @@

#define        JIFFIES_DIFF(n, j)      ((j) - (n))

-static DECLARE_TASK_QUEUE(tq_cyclades);
-
static struct tty_driver cy_serial_driver, cy_callout_driver;
static int serial_refcount;

@@ -934,8 +932,7 @@
cy_sched_event(struct cyclades_port *info, int event)
{
    info->event |= 1 << event; /* remember what kind of event and who */
-    queue_task(&info->tqueue, &tq_cyclades); /* it belongs to */
-    mark_bh(CYCLADES_BH);                       /* then trigger event */
+    queue_immediate_task(&info->tqueue); /* it belongs to */
} /* cy_sched_event */


@@ -962,12 +959,6 @@
 * had to poll every port to see if that port needed servicing.
 */
static void
-do_cyclades_bh(void)
-{
-    run_task_queue(&tq_cyclades);
-} /* do_cyclades_bh */
-
-static void
do_softint(void *private_)
{
  struct cyclades_port *info = (struct cyclades_port *) private_;
@@ -5513,8 +5504,6 @@
  unsigned short chip_number;
  int nports;

-    init_bh(CYCLADES_BH, do_cyclades_bh);
-
    show_version();

    /* Initialize the tty_driver structure */
@@ -5791,7 +5780,6 @@
#endif /* CONFIG_CYZ_INTR */

    save_flags(flags); cli();
-    remove_bh(CYCLADES_BH);

    if ((e1 = tty_unregister_driver(&cy_serial_driver)))
            printk("cyc: failed to unregister Cyclades serial driver(%d)\n",
diff -urNX dontdiff linux-2.5.22/drivers/char/drm/gamma_dma.c linux-2.5.22-bh/drivers/char/drm/gamma_dma.c
--- linux-2.5.22/drivers/char/drm/gamma_dma.c   Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/char/drm/gamma_dma.c        Mon Jun 17 11:54:32 2002
@@ -126,8 +126,7 @@
               clear_bit(0, &dev->dma_flag);

                               /* Dispatch new buffer */
-               queue_task(&dev->tq, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&dev->tq);
       }
}

diff -urNX dontdiff linux-2.5.22/drivers/char/drm/i830_dma.c linux-2.5.22-bh/drivers/char/drm/i830_dma.c
--- linux-2.5.22/drivers/char/drm/i830_dma.c    Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/char/drm/i830_dma.c Mon Jun 17 11:53:32 2002
@@ -1077,8 +1077,7 @@
       else
          return;

-       queue_task(&dev->tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&dev->tq);
}

void DRM(dma_immediate_bh)(void *device)
diff -urNX dontdiff linux-2.5.22/drivers/char/dz.c linux-2.5.22-bh/drivers/char/dz.c
--- linux-2.5.22/drivers/char/dz.c      Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/char/dz.c   Mon Jun 17 13:01:09 2002
@@ -73,8 +73,6 @@

#define DZ_INTR_DEBUG 1

-DECLARE_TASK_QUEUE(tq_serial);
-
static struct dz_serial *lines[4];
static unsigned char tmp_buffer[256];

@@ -189,8 +187,7 @@
static inline void dz_sched_event (struct dz_serial *info, int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

/*
@@ -400,11 +397,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh (void)
-{
-       run_task_queue (&tq_serial);
-}
-
static void do_softint (void *private_data)
{
       struct dz_serial *info = (struct dz_serial *) private_data;
@@ -1326,9 +1318,6 @@
{
       int i, flags;
       struct dz_serial *info;
-
-       /* Setup base handler, and timer table. */
-       init_bh(SERIAL_BH, do_serial_bh);

       show_serial_version();

diff -urNX dontdiff linux-2.5.22/drivers/char/esp.c linux-2.5.22-bh/drivers/char/esp.c
--- linux-2.5.22/drivers/char/esp.c     Sun Jun  2 18:44:38 2002
+++ linux-2.5.22-bh/drivers/char/esp.c  Mon Jun 17 13:00:25 2002
@@ -107,8 +107,6 @@
static char serial_name[] __initdata = "ESP serial driver";
static char serial_version[] __initdata = "2.2";

-static DECLARE_TASK_QUEUE(tq_esp);
-
static struct tty_driver esp_driver, esp_callout_driver;
static int serial_refcount;

@@ -278,8 +276,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_esp);
-       mark_bh(ESP_BH);
+       queue_immediate_task(&info->tqueue);
}
static _INLINE_ struct esp_pio_buffer *get_pio_buffer(void)
{
@@ -770,11 +767,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_esp);
-}
-
static void do_softint(void *private_)
{
       struct esp_struct       *info = (struct esp_struct *) private_;
@@ -2511,8 +2503,6 @@
       struct esp_struct *last_primary = 0;
       int esp[] = {0x100,0x140,0x180,0x200,0x240,0x280,0x300,0x380};

-       init_bh(ESP_BH, do_serial_bh);
-
       for (i = 0; i < NR_PRIMARY; i++) {
               if (irq[i] != 0) {
                       if ((irq[i] < 2) || (irq[i] > 15) || (irq[i] == 6) ||
@@ -2715,7 +2705,6 @@
       /* printk("Unloading %s: version %s\n", serial_name, serial_version); */
       save_flags(flags);
       cli();
-       remove_bh(ESP_BH);
       if ((e1 = tty_unregister_driver(&esp_driver)))
               printk("SERIAL: failed to unregister serial driver (%d)\n",
                      e1);
diff -urNX dontdiff linux-2.5.22/drivers/char/ip2/i2lib.c linux-2.5.22-bh/drivers/char/ip2/i2lib.c
--- linux-2.5.22/drivers/char/ip2/i2lib.c       Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/char/ip2/i2lib.c    Mon Jun 17 11:53:14 2002
@@ -1582,8 +1582,7 @@
                       WRITE_UNLOCK_IRQRESTORE(&pB->read_fifo_spinlock,bflags);

#ifdef USE_IQ
-                       queue_task(&pCh->tqueue_input, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&pCh->tqueue_input);
#else
                       do_input(pCh);
#endif
@@ -1820,8 +1819,7 @@
                                       }  /* End of switch on status type */
                                       if (dss_change) {
#ifdef USE_IQ
-                                               queue_task(&pCh->tqueue_status, &tq_immediate);
-                                               mark_bh(IMMEDIATE_BH);
+                                               queue_immediate_task(&pCh->tqueue_status);
#else
                                               do_status(pCh);
#endif
diff -urNX dontdiff linux-2.5.22/drivers/char/ip2main.c linux-2.5.22-bh/drivers/char/ip2main.c
--- linux-2.5.22/drivers/char/ip2main.c Sun Jun  2 18:44:50 2002
+++ linux-2.5.22-bh/drivers/char/ip2main.c      Mon Jun 17 12:04:22 2002
@@ -1386,10 +1386,7 @@
                       iiDisableMailIrq(pB);

//                     Park the board on the immediate queue for processing.
-                       queue_task(&pB->tqueue_interrupt, &tq_immediate);
-
-//                     Make sure the immediate queue is flagged to fire.
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&pB->tqueue_interrupt);
                   }
#else
//             We are using immediate servicing here.  This sucks and can
diff -urNX dontdiff linux-2.5.22/drivers/char/isicom.c linux-2.5.22-bh/drivers/char/isicom.c
--- linux-2.5.22/drivers/char/isicom.c  Mon Jun 17 04:49:04 2002
+++ linux-2.5.22-bh/drivers/char/isicom.c       Mon Jun 17 13:00:39 2002
@@ -84,8 +84,6 @@
static struct isi_board isi_card[BOARD_COUNT];
static struct isi_port  isi_ports[PORT_COUNT];

-DECLARE_TASK_QUEUE(tq_isicom);
-
static struct timer_list tx;
static char re_schedule = 1;
#ifdef ISICOM_DEBUG
@@ -360,8 +358,7 @@

extern inline void schedule_bh(struct isi_port * port)
{
-       queue_task(&port->bh_tqueue, &tq_isicom);
-       mark_bh(ISICOM_BH);
+       queue_immediate_task(&port->bh_tqueue);
}

/*     Transmitter     */
@@ -487,13 +484,6 @@

/*     Interrupt handlers      */

-static void do_isicom_bh(void)
-{
-       run_task_queue(&tq_isicom);
-}
-
-
-
static void isicom_bottomhalf(void * data)
{
       struct isi_port * port = (struct isi_port *) data;
@@ -1886,10 +1876,6 @@
               return 0;
       }

-       /* initialize bottom half  */
-       init_bh(ISICOM_BH, do_isicom_bh);
-
-
       memset(isi_ports, 0, sizeof(isi_ports));
       for (card = 0; card < BOARD_COUNT; card++) {
               port = &isi_ports[card * 16];
@@ -2037,8 +2023,6 @@
       set_current_state(TASK_INTERRUPTIBLE);
       schedule_timeout(HZ);

-       remove_bh(ISICOM_BH);
-
#ifdef ISICOM_DEBUG
       printk("ISICOM: isicom_tx tx_count = %ld.\n", tx_count);
#endif
diff -urNX dontdiff linux-2.5.22/drivers/char/pcmcia/synclink_cs.c linux-2.5.22-bh/drivers/char/pcmcia/synclink_cs.c
--- linux-2.5.22/drivers/char/pcmcia/synclink_cs.c      Sun Jun  2 18:44:46 2002
+++ linux-2.5.22-bh/drivers/char/pcmcia/synclink_cs.c   Mon Jun 17 11:54:59 2002
@@ -1460,8 +1460,7 @@
               if ( debug_level >= DEBUG_LEVEL_ISR )
                       printk("%s(%d):%s queueing bh task.\n",
                               __FILE__,__LINE__,info->device_name);
-               queue_task(&info->task, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&info->task);
               info->bh_requested = 1;
       }

diff -urNX dontdiff linux-2.5.22/drivers/char/pcxx.c linux-2.5.22-bh/drivers/char/pcxx.c
--- linux-2.5.22/drivers/char/pcxx.c    Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/char/pcxx.c Mon Jun 17 13:00:54 2002
@@ -150,8 +150,6 @@

static struct timer_list pcxx_timer;

-DECLARE_TASK_QUEUE(tq_pcxx);
-
static void pcxxpoll(unsigned long dummy);
static void pcxxdelay(int);
static void fepcmd(struct channel *, int, int, int, int, int);
@@ -170,7 +168,6 @@
static void pcxxparam(struct tty_struct *, struct channel *ch);
static void do_softint(void *);
static inline void pcxe_sched_event(struct channel *, int);
-static void do_pcxe_bh(void);
static void pcxe_start(struct tty_struct *);
static void pcxe_stop(struct tty_struct *);
static void pcxe_throttle(struct tty_struct *);
@@ -237,7 +234,6 @@
       save_flags(flags);
       cli();
       del_timer_sync(&pcxx_timer);
-       remove_bh(DIGI_BH);

       if ((e1 = tty_unregister_driver(&pcxe_driver)))
               printk("SERIAL: failed to unregister serial driver (%d)\n", e1);
@@ -327,8 +323,7 @@
static inline void pcxe_sched_event(struct channel *info, int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_pcxx);
-       mark_bh(DIGI_BH);
+       queue_immediate_task(&info->tqueue);
}

static void pcxx_error(int line, char *msg)
@@ -1222,8 +1217,6 @@
       }
       memset(pcxe_termios_locked,0,sizeof(struct termios *)*nbdevs);

-       init_bh(DIGI_BH,do_pcxe_bh);
-
       init_timer(&pcxx_timer);
       pcxx_timer.function = pcxxpoll;

@@ -2372,12 +2365,6 @@
                       wake_up_interruptible(&info->open_wait);
               restore_flags(flags);
       }
-}
-
-
-static void do_pcxe_bh(void)
-{
-       run_task_queue(&tq_pcxx);
}


diff -urNX dontdiff linux-2.5.22/drivers/char/random.c linux-2.5.22-bh/drivers/char/random.c
--- linux-2.5.22/drivers/char/random.c  Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/char/random.c       Mon Jun 17 12:58:18 2002
@@ -252,6 +252,7 @@
#include <linux/poll.h>
#include <linux/init.h>
#include <linux/fs.h>
+#include <linux/tqueue.h>

#include <asm/processor.h>
#include <asm/uaccess.h>
diff -urNX dontdiff linux-2.5.22/drivers/char/rio/func.h linux-2.5.22-bh/drivers/char/rio/func.h
--- linux-2.5.22/drivers/char/rio/func.h        Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/char/rio/func.h     Mon Jun 17 06:44:20 2002
@@ -39,6 +39,8 @@
#endif
#endif

+#include <linux/kdev_t.h>
+
/* rioboot.c */
int RIOBootCodeRTA(struct rio_info *, struct DownLoad *);
int RIOBootCodeHOST(struct rio_info *, register struct DownLoad *);
diff -urNX dontdiff linux-2.5.22/drivers/char/riscom8.c linux-2.5.22-bh/drivers/char/riscom8.c
--- linux-2.5.22/drivers/char/riscom8.c Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/char/riscom8.c      Mon Jun 17 13:02:18 2002
@@ -81,8 +81,6 @@

#define RS_EVENT_WRITE_WAKEUP  0

-static DECLARE_TASK_QUEUE(tq_riscom);
-
#define RISCOM_TYPE_NORMAL     1
#define RISCOM_TYPE_CALLOUT    2

@@ -339,17 +337,8 @@

static inline void rc_mark_event(struct riscom_port * port, int event)
{
-       /*
-         * I'm not quite happy with current scheme all serial
-        * drivers use their own BH routine.
-         * It seems this easily can be done with one BH routine
-        * serving for all serial drivers.
-        * For now I must introduce another one - RISCOM8_BH.
-        * Still hope this will be changed in near future.
-         */
       set_bit(event, &port->event);
-       queue_task(&port->tqueue, &tq_riscom);
-       mark_bh(RISCOM8_BH);
+       queue_immediate_task(&port->tqueue);
}

static inline struct riscom_port * rc_get_port(struct riscom_board const * bp,
@@ -1720,11 +1709,6 @@
       }
}

-static void do_riscom_bh(void)
-{
-        run_task_queue(&tq_riscom);
-}
-
static void do_softint(void *private_)
{
       struct riscom_port      *port = (struct riscom_port *) private_;
@@ -1751,7 +1735,6 @@
               printk(KERN_ERR "rc: Couldn't get free page.\n");
               return 1;
       }
-       init_bh(RISCOM8_BH, do_riscom_bh);
       memset(IRQ_to_board, 0, sizeof(IRQ_to_board));
       memset(&riscom_driver, 0, sizeof(riscom_driver));
       riscom_driver.magic = TTY_DRIVER_MAGIC;
@@ -1830,7 +1813,6 @@

       save_flags(flags);
       cli();
-       remove_bh(RISCOM8_BH);
       free_page((unsigned long)tmp_buf);
       tty_unregister_driver(&riscom_driver);
       tty_unregister_driver(&riscom_callout_driver);
diff -urNX dontdiff linux-2.5.22/drivers/char/serial.c linux-2.5.22-bh/drivers/char/serial.c
--- linux-2.5.22/drivers/char/serial.c  Sun Jun  2 18:44:45 2002
+++ linux-2.5.22-bh/drivers/char/serial.c       Mon Jun 17 13:01:48 2002
@@ -245,8 +245,6 @@

static char *serial_name = "Serial driver";

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -560,8 +558,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static _INLINE_ void receive_chars(struct async_struct *info,
@@ -1036,11 +1033,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct async_struct     *info = (struct async_struct *) private_;
@@ -5373,7 +5365,6 @@
       int i;
       struct serial_state * state;

-       init_bh(SERIAL_BH, do_serial_bh);
       init_timer(&serial_timer);
       serial_timer.function = rs_timer;
       mod_timer(&serial_timer, jiffies + RS_STROBE_TIME);
@@ -5702,7 +5693,6 @@
       /* printk("Unloading %s: version %s\n", serial_name, serial_version); */
       del_timer_sync(&serial_timer);
       save_flags(flags); cli();
-        remove_bh(SERIAL_BH);
       if ((e1 = tty_unregister_driver(&serial_driver)))
               printk("serial: failed to unregister serial driver (%d)\n",
                      e1);
diff -urNX dontdiff linux-2.5.22/drivers/char/serial167.c linux-2.5.22-bh/drivers/char/serial167.c
--- linux-2.5.22/drivers/char/serial167.c       Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/char/serial167.c    Mon Jun 17 13:02:05 2002
@@ -99,8 +99,6 @@
#define SERIAL_TYPE_CALLOUT 2


-DECLARE_TASK_QUEUE(tq_cyclades);
-
struct tty_driver cy_serial_driver, cy_callout_driver;
extern int serial_console;
static struct cyclades_port *serial_console_info = NULL;
@@ -390,8 +388,7 @@
cy_sched_event(struct cyclades_port *info, int event)
{
    info->event |= 1 << event; /* remember what kind of event and who */
-    queue_task(&info->tqueue, &tq_cyclades); /* it belongs to */
-    mark_bh(CYCLADES_BH);                       /* then trigger event */
+    queue_immediate_task(&info->tqueue); /* it belongs to */
} /* cy_sched_event */


@@ -746,12 +743,6 @@
 * had to poll every port to see if that port needed servicing.
 */
static void
-do_cyclades_bh(void)
-{
-    run_task_queue(&tq_cyclades);
-} /* do_cyclades_bh */
-
-static void
do_softint(void *private_)
{
  struct cyclades_port *info = (struct cyclades_port *) private_;
@@ -2443,8 +2434,6 @@
           printk(KERN_ERR "Couldn't register MVME166/7 callout driver\n");
           goto cleanup_serial_driver;
    }
-
-    init_bh(CYCLADES_BH, do_cyclades_bh);

    port_num = 0;
    info = cy_port;
diff -urNX dontdiff linux-2.5.22/drivers/char/sh-sci.c linux-2.5.22-bh/drivers/char/sh-sci.c
--- linux-2.5.22/drivers/char/sh-sci.c  Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/char/sh-sci.c       Mon Jun 17 12:03:52 2002
@@ -431,8 +431,7 @@
static inline void sci_sched_event(struct sci_port *port, int event)
{
       port->event |= 1 << event;
-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);
}

static void sci_transmit_chars(struct sci_port *port)
diff -urNX dontdiff linux-2.5.22/drivers/char/specialix.c linux-2.5.22-bh/drivers/char/specialix.c
--- linux-2.5.22/drivers/char/specialix.c       Sun Jun  2 18:44:52 2002
+++ linux-2.5.22-bh/drivers/char/specialix.c    Mon Jun 17 13:02:30 2002
@@ -172,8 +172,6 @@
#define MIN(a,b) ((a) < (b) ? (a) : (b))
#endif

-DECLARE_TASK_QUEUE(tq_specialix);
-
#undef RS_EVENT_WRITE_WAKEUP
#define RS_EVENT_WRITE_WAKEUP  0

@@ -601,18 +599,8 @@

extern inline void sx_mark_event(struct specialix_port * port, int event)
{
-       /*
-        * I'm not quite happy with current scheme all serial
-        * drivers use their own BH routine.
-        * It seems this easily can be done with one BH routine
-        * serving for all serial drivers.
-        * For now I must introduce another one - SPECIALIX_BH.
-        * Still hope this will be changed in near future.
-        * -- Dmitry.
-        */
       set_bit(event, &port->event);
-       queue_task(&port->tqueue, &tq_specialix);
-       mark_bh(SPECIALIX_BH);
+       queue_immediate_task(&port->tqueue);
}


@@ -2197,12 +2185,6 @@
}


-static void do_specialix_bh(void)
-{
-        run_task_queue(&tq_specialix);
-}
-
-
static void do_softint(void *private_)
{
       struct specialix_port   *port = (struct specialix_port *) private_;
@@ -2230,7 +2212,6 @@
               printk(KERN_ERR "sx: Couldn't get free page.\n");
               return 1;
       }
-       init_bh(SPECIALIX_BH, do_specialix_bh);
       memset(&specialix_driver, 0, sizeof(specialix_driver));
       specialix_driver.magic = TTY_DRIVER_MAGIC;
       specialix_driver.name = "ttyW";
diff -urNX dontdiff linux-2.5.22/drivers/char/synclink.c linux-2.5.22-bh/drivers/char/synclink.c
--- linux-2.5.22/drivers/char/synclink.c        Sun Jun  2 18:44:47 2002
+++ linux-2.5.22-bh/drivers/char/synclink.c     Mon Jun 17 12:02:05 2002
@@ -1757,8 +1757,7 @@
               if ( debug_level >= DEBUG_LEVEL_ISR )
                       printk("%s(%d):%s queueing bh task.\n",
                               __FILE__,__LINE__,info->device_name);
-               queue_task(&info->task, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&info->task);
               info->bh_requested = 1;
       }

diff -urNX dontdiff linux-2.5.22/drivers/char/synclinkmp.c linux-2.5.22-bh/drivers/char/synclinkmp.c
--- linux-2.5.22/drivers/char/synclinkmp.c      Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/drivers/char/synclinkmp.c   Mon Jun 17 12:01:49 2002
@@ -2572,8 +2572,7 @@
                       if ( debug_level >= DEBUG_LEVEL_ISR )
                               printk("%s(%d):%s queueing bh task.\n",
                                       __FILE__,__LINE__,port->device_name);
-                       queue_task(&port->task, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&port->task);
                       port->bh_requested = 1;
               }
       }
diff -urNX dontdiff linux-2.5.22/drivers/isdn/act2000/act2000.h linux-2.5.22-bh/drivers/isdn/act2000/act2000.h
--- linux-2.5.22/drivers/isdn/act2000/act2000.h Sun Jun  2 18:44:37 2002
+++ linux-2.5.22-bh/drivers/isdn/act2000/act2000.h      Mon Jun 17 11:37:39 2002
@@ -179,20 +179,17 @@

extern __inline__ void act2000_schedule_tx(act2000_card *card)
{
-        queue_task(&card->snd_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->snd_tq);
}

extern __inline__ void act2000_schedule_rx(act2000_card *card)
{
-        queue_task(&card->rcv_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->rcv_tq);
}

extern __inline__ void act2000_schedule_poll(act2000_card *card)
{
-        queue_task(&card->poll_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->poll_tq);
}

extern char *act2000_find_eaz(act2000_card *, char);
diff -urNX dontdiff linux-2.5.22/drivers/isdn/capi/kcapi.c linux-2.5.22-bh/drivers/isdn/capi/kcapi.c
--- linux-2.5.22/drivers/isdn/capi/kcapi.c      Sun Jun  2 18:44:52 2002
+++ linux-2.5.22-bh/drivers/isdn/capi/kcapi.c   Mon Jun 17 11:52:40 2002
@@ -359,8 +359,7 @@

       }
       skb_queue_tail(&recv_queue, skb);
-       queue_task(&tq_recv_notify, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&tq_recv_notify);
       return;

error:
diff -urNX dontdiff linux-2.5.22/drivers/isdn/eicon/eicon.h linux-2.5.22-bh/drivers/isdn/eicon/eicon.h
--- linux-2.5.22/drivers/isdn/eicon/eicon.h     Sun Jun  2 18:44:45 2002
+++ linux-2.5.22-bh/drivers/isdn/eicon/eicon.h  Mon Jun 17 11:28:18 2002
@@ -349,20 +349,17 @@

extern __inline__ void eicon_schedule_tx(eicon_card *card)
{
-        queue_task(&card->snd_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->snd_tq);
}

extern __inline__ void eicon_schedule_rx(eicon_card *card)
{
-        queue_task(&card->rcv_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->rcv_tq);
}

extern __inline__ void eicon_schedule_ack(eicon_card *card)
{
-        queue_task(&card->ack_tq, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&card->ack_tq);
}

extern int eicon_addcard(int, int, int, char *, int);
diff -urNX dontdiff linux-2.5.22/drivers/isdn/eicon/linsys.c linux-2.5.22-bh/drivers/isdn/eicon/linsys.c
--- linux-2.5.22/drivers/isdn/eicon/linsys.c    Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/isdn/eicon/linsys.c Mon Jun 17 11:30:06 2002
@@ -84,8 +84,7 @@
       DivasTask.routine = DivasDoDpc;
       DivasTask.data = (void *) 0;

-       queue_task(&DivasTask, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&DivasTask);

       return 0;
}
@@ -97,8 +96,7 @@
       DivasTask.routine = DivasDoRequestDpc;
       DivasTask.data = (void *) 0;

-       queue_task(&DivasTask, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&DivasTask);

       return 0;
}
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/amd7930.c linux-2.5.22-bh/drivers/isdn/hisax/amd7930.c
--- linux-2.5.22/drivers/isdn/hisax/amd7930.c   Sun Jun  2 18:44:47 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/amd7930.c        Mon Jun 17 11:44:26 2002
@@ -121,16 +121,14 @@
       } else {
               clear_bit(BC_FLG_BUSY, &bcs->Flag);
               bcs->event |= 1 << B_XMTBUFREADY;
-               queue_task(&bcs->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&bcs->tqueue);
       }
}

static void
Bchan_xmit_callback(struct BCState *bcs)
{
-       queue_task(&bcs->hw.amd7930.tq_xmt, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->hw.amd7930.tq_xmt);
}

/* B channel transmission: two modes (three, if you count L1_MODE_NULL)
@@ -262,8 +260,7 @@
                             (void *) &Bchan_recv_callback, (void *) bcs);
       }

-       queue_task(&hw->tq_rcv, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&hw->tq_rcv);
}

static void
@@ -309,7 +306,7 @@
                                               skb_queue_tail(&bcs->rqueue, hw->rv_skb);
                                               hw->rv_skb = skb;
                                               bcs->event |= 1 << B_RCVBUFREADY;
-                                               queue_task(&bcs->tqueue, &tq_immediate);
+                                               queue_immediate_task(&bcs->tqueue);
                                       }
                               } else if (len > 0) {
                                       /* Small packet received */
@@ -320,8 +317,7 @@
                                               memcpy(skb_put(skb, len), hw->rv_skb->tail, len);
                                               skb_queue_tail(&bcs->rqueue, skb);
                                               bcs->event |= 1 << B_RCVBUFREADY;
-                                               queue_task(&bcs->tqueue, &tq_immediate);
-                                               mark_bh(IMMEDIATE_BH);
+                                               queue_immediate_task(&bcs->tqueue);
                                       }
                               } else {
                                       /* Reception Error */
@@ -337,8 +333,7 @@
                                      RCV_BUFSIZE/RCV_BUFBLKS);
                               skb_queue_tail(&bcs->rqueue, skb);
                               bcs->event |= 1 << B_RCVBUFREADY;
-                               queue_task(&bcs->tqueue, &tq_immediate);
-                               mark_bh(IMMEDIATE_BH);
+                               queue_immediate_task(&bcs->tqueue);
                       }
               }

@@ -482,8 +477,7 @@

               task.routine = (void *) DChannel_proc_rcv;
               task.data = (void *) cs;
-               queue_task(&task, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&task);
       }

       if (cs->debug & L1_DEB_ISAC_FIFO) {
@@ -524,8 +518,7 @@

       task.routine = (void *) DChannel_proc_xmt;
       task.data = (void *) cs;
-       queue_task(&task, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&task);
}

static void
@@ -658,8 +651,7 @@
       task.sync = 0;
       task.routine = (void *) &amd7930_new_ph;
       task.data = (void *) cs;
-       queue_task(&task, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&task);
}

void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/amd7930_fn.c linux-2.5.22-bh/drivers/isdn/hisax/amd7930_fn.c
--- linux-2.5.22/drivers/isdn/hisax/amd7930_fn.c        Mon Jun 17 04:49:05 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/amd7930_fn.c     Mon Jun 17 11:50:01 2002
@@ -278,8 +278,7 @@
        }

        test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

static void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/avm_pci.c linux-2.5.22-bh/drivers/isdn/hisax/avm_pci.c
--- linux-2.5.22/drivers/isdn/hisax/avm_pci.c   Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/avm_pci.c        Mon Jun 17 11:41:25 2002
@@ -201,8 +201,7 @@
hdlc_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/config.c linux-2.5.22-bh/drivers/isdn/hisax/config.c
--- linux-2.5.22/drivers/isdn/hisax/config.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/config.c Mon Jun 17 11:48:53 2002
@@ -1818,8 +1818,7 @@
static void hisax_sched_event(struct IsdnCardState *cs, int event)
{
       cs->event |= 1 << event;
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

static void hisax_bh(struct IsdnCardState *cs)
@@ -1845,8 +1844,7 @@
static void hisax_b_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

static inline void D_L2L1(struct hisax_d_if *d_if, int pr, void *arg)
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/hfc_2bds0.c linux-2.5.22-bh/drivers/isdn/hisax/hfc_2bds0.c
--- linux-2.5.22/drivers/isdn/hisax/hfc_2bds0.c Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/hfc_2bds0.c      Mon Jun 17 11:39:08 2002
@@ -203,8 +203,7 @@
hfc_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

static struct sk_buff
@@ -647,8 +646,7 @@
sched_event_D(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

static
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/hfc_2bs0.c linux-2.5.22-bh/drivers/isdn/hisax/hfc_2bs0.c
--- linux-2.5.22/drivers/isdn/hisax/hfc_2bs0.c  Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/hfc_2bs0.c       Mon Jun 17 11:40:00 2002
@@ -87,8 +87,7 @@
hfc_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

static void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/hfc_pci.c linux-2.5.22-bh/drivers/isdn/hisax/hfc_pci.c
--- linux-2.5.22/drivers/isdn/hisax/hfc_pci.c   Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/hfc_pci.c        Mon Jun 17 11:44:52 2002
@@ -195,8 +195,7 @@
sched_event_D_pci(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

/*********************************/
@@ -206,8 +205,7 @@
hfcpci_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

/************************************************/
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/hfc_sx.c linux-2.5.22-bh/drivers/isdn/hisax/hfc_sx.c
--- linux-2.5.22/drivers/isdn/hisax/hfc_sx.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/hfc_sx.c Mon Jun 17 11:39:42 2002
@@ -465,8 +465,7 @@
sched_event_D_sx(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

/*********************************/
@@ -476,8 +475,7 @@
hfcsx_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

/************************************************/
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/hscx.c linux-2.5.22-bh/drivers/isdn/hisax/hscx.c
--- linux-2.5.22/drivers/isdn/hisax/hscx.c      Sun Jun  2 18:44:39 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/hscx.c   Mon Jun 17 11:37:57 2002
@@ -96,8 +96,7 @@
hscx_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/icc.c linux-2.5.22-bh/drivers/isdn/hisax/icc.c
--- linux-2.5.22/drivers/isdn/hisax/icc.c       Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/icc.c    Mon Jun 17 11:38:19 2002
@@ -192,8 +192,7 @@
icc_sched_event(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/ipacx.c linux-2.5.22-bh/drivers/isdn/hisax/ipacx.c
--- linux-2.5.22/drivers/isdn/hisax/ipacx.c     Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/ipacx.c  Mon Jun 17 11:50:53 2002
@@ -311,8 +311,7 @@
dch_sched_event(struct IsdnCardState *cs, int event)
{
       set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

//----------------------------------------------------------
@@ -603,8 +602,7 @@
bch_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

//----------------------------------------------------------
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/isac.c linux-2.5.22-bh/drivers/isdn/hisax/isac.c
--- linux-2.5.22/drivers/isdn/hisax/isac.c      Sun Jun  2 18:44:42 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/isac.c   Mon Jun 17 11:40:19 2002
@@ -196,8 +196,7 @@
isac_sched_event(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/isar.c linux-2.5.22-bh/drivers/isdn/hisax/isar.c
--- linux-2.5.22/drivers/isdn/hisax/isar.c      Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/isar.c   Mon Jun 17 11:47:57 2002
@@ -448,8 +448,7 @@
isar_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

static inline void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/jade.c linux-2.5.22-bh/drivers/isdn/hisax/jade.c
--- linux-2.5.22/drivers/isdn/hisax/jade.c      Sun Jun  2 18:44:46 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/jade.c   Mon Jun 17 11:41:11 2002
@@ -139,8 +139,7 @@
jade_sched_event(struct BCState *bcs, int event)
{
    bcs->event |= 1 << event;
-    queue_task(&bcs->tqueue, &tq_immediate);
-    mark_bh(IMMEDIATE_BH);
+    queue_immediate_task(&bcs->tqueue);
}

static void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/netjet.c linux-2.5.22-bh/drivers/isdn/hisax/netjet.c
--- linux-2.5.22/drivers/isdn/hisax/netjet.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/netjet.c Mon Jun 17 11:40:57 2002
@@ -435,8 +435,7 @@
               skb_queue_tail(&bcs->rqueue, skb);
       }
       bcs->event |= 1 << B_RCVBUFREADY;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);

       if (bcs->cs->debug & L1_DEB_RECEIVE_FRAME)
               printframe(bcs->cs, bcs->hw.tiger.rcvbuf, count, "rec");
@@ -792,8 +791,7 @@
                                                       cnt - s_cnt);
                               }
                               bcs->event |= 1 << B_XMTBUFREADY;
-                               queue_task(&bcs->tqueue, &tq_immediate);
-                               mark_bh(IMMEDIATE_BH);
+                               queue_immediate_task(&bcs->tqueue);
                       }
               }
       } else if (test_and_clear_bit(BC_FLG_NOFRAME, &bcs->Flag)) {
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hisax/w6692.c linux-2.5.22-bh/drivers/isdn/hisax/w6692.c
--- linux-2.5.22/drivers/isdn/hisax/w6692.c     Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hisax/w6692.c  Mon Jun 17 11:49:26 2002
@@ -136,16 +136,14 @@
W6692_sched_event(struct IsdnCardState *cs, int event)
{
       test_and_set_bit(event, &cs->event);
-       queue_task(&cs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&cs->tqueue);
}

static void
W6692B_sched_event(struct BCState *bcs, int event)
{
       bcs->event |= 1 << event;
-       queue_task(&bcs->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bcs->tqueue);
}

static void
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hysdn/boardergo.c linux-2.5.22-bh/drivers/isdn/hysdn/boardergo.c
--- linux-2.5.22/drivers/isdn/hysdn/boardergo.c Sun Jun  2 18:44:50 2002
+++ linux-2.5.22-bh/drivers/isdn/hysdn/boardergo.c      Mon Jun 17 11:34:54 2002
@@ -60,8 +60,7 @@

       /* start kernel task immediately after leaving all interrupts */
       if (!card->hw_lock) {
-               queue_task(&card->irq_queue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&card->irq_queue);
       }
       restore_flags(flags);
}                              /* ergo_interrupt */
@@ -177,8 +176,7 @@
               card->err_log_state = ERRLOG_STATE_STOP;        /* request stop */

       restore_flags(flags);
-       queue_task(&card->irq_queue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&card->irq_queue);
}                              /* ergo_set_errlog_state */

/******************************************/
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hysdn/hycapi.c linux-2.5.22-bh/drivers/isdn/hysdn/hycapi.c
--- linux-2.5.22/drivers/isdn/hysdn/hycapi.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/hysdn/hycapi.c Mon Jun 17 11:31:28 2002
@@ -131,8 +131,7 @@
       }
       cinfo->tx_skb = skb;
       spin_unlock_irq(&cinfo->lock);
-       queue_task(&card->irq_queue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&card->irq_queue);
}

/***********************************************************
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hysdn/hysdn_net.c linux-2.5.22-bh/drivers/isdn/hysdn/hysdn_net.c
--- linux-2.5.22/drivers/isdn/hysdn/hysdn_net.c Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/isdn/hysdn/hysdn_net.c      Mon Jun 17 11:31:10 2002
@@ -170,8 +170,7 @@
       spin_unlock_irq(&lp->lock);

       if (lp->sk_count <= 3) {
-               queue_task(&((hysdn_card *) dev->priv)->irq_queue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&((hysdn_card *) dev->priv)->irq_queue);
       }
       return (0);             /* success */
}                              /* net_send_packet */
diff -urNX dontdiff linux-2.5.22/drivers/isdn/hysdn/hysdn_sched.c linux-2.5.22-bh/drivers/isdn/hysdn/hysdn_sched.c
--- linux-2.5.22/drivers/isdn/hysdn/hysdn_sched.c       Sun Jun  2 18:44:42 2002
+++ linux-2.5.22-bh/drivers/isdn/hysdn/hysdn_sched.c    Mon Jun 17 11:34:14 2002
@@ -175,8 +175,7 @@
       card->async_busy = 1;   /* request transfer */

       /* now queue the task */
-       queue_task(&card->irq_queue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&card->irq_queue);
       sti();

       if (card->debug_flags & LOG_SCHED_ASYN)
diff -urNX dontdiff linux-2.5.22/drivers/isdn/i4l/isdn_net.c linux-2.5.22-bh/drivers/isdn/i4l/isdn_net.c
--- linux-2.5.22/drivers/isdn/i4l/isdn_net.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/isdn/i4l/isdn_net.c Mon Jun 17 11:30:50 2002
@@ -151,8 +151,7 @@

       if (!(isdn_net_device_busy(lp))) {
               if (!skb_queue_empty(&lp->super_tx_queue)) {
-                       queue_task(&lp->tqueue, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&lp->tqueue);
               } else {
                       isdn_net_device_wake_queue(lp);
               }
@@ -997,8 +996,7 @@
               // we can't grab the lock from irq context,
               // so we just queue the packet
               skb_queue_tail(&lp->super_tx_queue, skb);
-               queue_task(&lp->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&lp->tqueue);
               return;
       }

diff -urNX dontdiff linux-2.5.22/drivers/isdn/pcbit/layer2.c linux-2.5.22-bh/drivers/isdn/pcbit/layer2.c
--- linux-2.5.22/drivers/isdn/pcbit/layer2.c    Sun Jun  2 18:44:52 2002
+++ linux-2.5.22-bh/drivers/isdn/pcbit/layer2.c Mon Jun 17 11:51:23 2002
@@ -81,8 +81,7 @@
static __inline__ void
pcbit_sched_delivery(struct pcbit_dev *dev)
{
-       queue_task(&dev->qdelivery, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&dev->qdelivery);
}


diff -urNX dontdiff linux-2.5.22/drivers/isdn/tpam/tpam_queues.c linux-2.5.22-bh/drivers/isdn/tpam/tpam_queues.c
--- linux-2.5.22/drivers/isdn/tpam/tpam_queues.c        Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/isdn/tpam/tpam_queues.c     Mon Jun 17 11:52:20 2002
@@ -36,8 +36,7 @@
       skb_queue_tail(&card->sendq, skb);

       /* queue the board's send task struct for immediate treatment */
-       queue_task(&card->send_tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&card->send_tq);
}

/*
@@ -58,8 +57,7 @@
               skb_queue_tail(&channel->sendq, skb);

       /* queue the channel's send task struct for immediate treatment */
-       queue_task(&channel->card->send_tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&channel->card->send_tq);
}

/*
@@ -169,8 +167,7 @@
               else {
                       /* put the message in the receive queue */
                       skb_queue_tail(&card->recvq, skb);
-                       queue_task(&card->recv_tq, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&card->recv_tq);
               }
               return;
       }
@@ -187,8 +184,7 @@
               spin_unlock(&card->lock);

               /* schedule the send queue for execution */
-               queue_task(&card->send_tq, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&card->send_tq);
               return;
       }

diff -urNX dontdiff linux-2.5.22/drivers/macintosh/macserial.c linux-2.5.22-bh/drivers/macintosh/macserial.c
--- linux-2.5.22/drivers/macintosh/macserial.c  Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/macintosh/macserial.c       Mon Jun 17 13:03:52 2002
@@ -104,8 +104,6 @@
#endif
#define ZS_CLOCK         3686400       /* Z8530 RTxC input clock rate */

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -372,8 +370,7 @@
                                 int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(MACSERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

/* Work out the flag value for a z8530 status value. */
@@ -721,11 +718,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using rs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct mac_serial       *info = (struct mac_serial *) private_;
@@ -2571,9 +2563,6 @@
       int channel, i;
       unsigned long flags;
       struct mac_serial *info;
-
-       /* Setup base handler, and timer table. */
-       init_bh(MACSERIAL_BH, do_serial_bh);

       /* Find out how many Z8530 SCCs we have */
       if (zs_chain == 0)
diff -urNX dontdiff linux-2.5.22/drivers/message/fusion/mptlan.c linux-2.5.22-bh/drivers/message/fusion/mptlan.c
--- linux-2.5.22/drivers/message/fusion/mptlan.c        Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/message/fusion/mptlan.c     Mon Jun 17 12:27:50 2002
@@ -855,8 +855,7 @@
       struct mpt_lan_priv *priv = dev->priv;

       if (test_and_set_bit(0, &priv->post_buckets_active) == 0) {
-               queue_task(&priv->post_buckets_task, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&priv->post_buckets_task);
               dioprintk((KERN_INFO MYNAM ": %s/%s: Queued post_buckets task.\n",
                               IOC_AND_NETDEV_NAMES_s_s(dev) ));
       }
diff -urNX dontdiff linux-2.5.22/drivers/message/i2o/i2o_lan.c linux-2.5.22-bh/drivers/message/i2o/i2o_lan.c
--- linux-2.5.22/drivers/message/i2o/i2o_lan.c  Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/drivers/message/i2o/i2o_lan.c       Mon Jun 17 12:28:05 2002
@@ -386,8 +386,7 @@

       if (atomic_read(&priv->buckets_out) <= priv->max_buckets_out - priv->bucket_thresh) {
               run_i2o_post_buckets_task.data = (void *)dev;
-               queue_task(&run_i2o_post_buckets_task, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&run_i2o_post_buckets_task);
       }

       return;
diff -urNX dontdiff linux-2.5.22/drivers/net/aironet4500_core.c linux-2.5.22-bh/drivers/net/aironet4500_core.c
--- linux-2.5.22/drivers/net/aironet4500_core.c Sun Jun  2 18:44:38 2002
+++ linux-2.5.22-bh/drivers/net/aironet4500_core.c      Mon Jun 17 11:19:05 2002
@@ -2203,8 +2203,7 @@
#define AWC_QUEUE_BH {\
       if (!priv->bh_active && !priv->bh_running){\
               priv->bh_active = 1;\
-               queue_task(&priv->immediate_bh, &tq_immediate);\
-               mark_bh(IMMEDIATE_BH);\
+               queue_immediate_task(&priv->immediate_bh);\
       }\
       }

diff -urNX dontdiff linux-2.5.22/drivers/net/hamradio/dmascc.c linux-2.5.22-bh/drivers/net/hamradio/dmascc.c
--- linux-2.5.22/drivers/net/hamradio/dmascc.c  Sun Jun  2 18:44:48 2002
+++ linux-2.5.22-bh/drivers/net/hamradio/dmascc.c       Mon Jun 17 11:17:18 2002
@@ -1073,8 +1073,7 @@
         priv->rx_head = (priv->rx_head + 1) % NUM_RX_BUF;
         priv->rx_count++;
         /* Mark bottom half handler */
-         queue_task(&priv->rx_task, &tq_immediate);
-         mark_bh(IMMEDIATE_BH);
+         queue_immediate_task(&priv->rx_task);
       } else {
         priv->stats.rx_errors++;
         priv->stats.rx_over_errors++;
diff -urNX dontdiff linux-2.5.22/drivers/net/plip.c linux-2.5.22-bh/drivers/net/plip.c
--- linux-2.5.22/drivers/net/plip.c     Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/net/plip.c  Mon Jun 17 11:23:14 2002
@@ -380,8 +380,7 @@
       struct net_local *nl = (struct net_local *)dev->priv;

       if (nl->is_deferred) {
-               queue_task(&nl->immediate, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&nl->immediate);
       }
}

@@ -741,8 +740,7 @@
               if (snd->state != PLIP_PK_DONE) {
                       nl->connection = PLIP_CN_SEND;
                       spin_unlock_irq(&nl->lock);
-                       queue_task(&nl->immediate, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&nl->immediate);
                       enable_parport_interrupts (dev);
                       ENABLE(dev->irq);
                       return OK;
@@ -998,8 +996,7 @@
               rcv->state = PLIP_PK_TRIGGER;
               nl->connection = PLIP_CN_RECEIVE;
               nl->timeout_count = 0;
-               queue_task(&nl->immediate, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&nl->immediate);
               break;

       case PLIP_CN_RECEIVE:
@@ -1052,8 +1049,7 @@
               nl->connection = PLIP_CN_SEND;
               nl->timeout_count = 0;
       }
-       queue_task(&nl->immediate, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&nl->immediate);
       spin_unlock_irq(&nl->lock);

       return 0;
diff -urNX dontdiff linux-2.5.22/drivers/net/tlan.c linux-2.5.22-bh/drivers/net/tlan.c
--- linux-2.5.22/drivers/net/tlan.c     Sun Jun  2 18:44:42 2002
+++ linux-2.5.22-bh/drivers/net/tlan.c  Mon Jun 17 11:20:48 2002
@@ -1681,8 +1681,7 @@
               TLan_ReadAndClearStats( dev, TLAN_RECORD );
               outl( TLAN_HC_AD_RST, dev->base_addr + TLAN_HOST_CMD );

-               queue_task(&priv->tlan_tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&priv->tlan_tqueue);

               netif_wake_queue(dev);
               ack = 0;
diff -urNX dontdiff linux-2.5.22/drivers/net/wan/sdlamain.c linux-2.5.22-bh/drivers/net/wan/sdlamain.c
--- linux-2.5.22/drivers/net/wan/sdlamain.c     Mon Jun 17 04:49:06 2002
+++ linux-2.5.22-bh/drivers/net/wan/sdlamain.c  Mon Jun 17 11:19:58 2002
@@ -234,9 +234,9 @@

 * On each rx_interrupt, the whole task queue
 * (wanpipe_tq_custom) will be queued into
- * IMMEDIATE_BH via wanpipe_mark_bh() call.
+ * tq_immediate via wanpipe_mark_bh() call.

- * The IMMEDIATE_BH will execute run_wanpipe_tq()
+ * The tq_immediate will execute run_wanpipe_tq()
 * function, which will execute all pending,
 * tasks in wanpipe_tq_custom queue */

@@ -1306,8 +1306,7 @@
void wanpipe_mark_bh (void)
{
       if (!test_and_set_bit(0,(void*)&wanpipe_bh_critical)){
-               queue_task(&wanpipe_tq_task,&tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&wanpipe_tq_task);
               clear_bit(0,(void*)&wanpipe_bh_critical);
       }
}
diff -urNX dontdiff linux-2.5.22/drivers/pcmcia/pci_socket.c linux-2.5.22-bh/drivers/pcmcia/pci_socket.c
--- linux-2.5.22/drivers/pcmcia/pci_socket.c    Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/drivers/pcmcia/pci_socket.c Mon Jun 17 13:10:15 2002
@@ -20,6 +20,7 @@
#include <linux/init.h>
#include <linux/pci.h>
#include <linux/sched.h>
+#include <linux/tqueue.h>
#include <linux/interrupt.h>

#include <pcmcia/ss.h>
diff -urNX dontdiff linux-2.5.22/drivers/pcmcia/yenta.c linux-2.5.22-bh/drivers/pcmcia/yenta.c
--- linux-2.5.22/drivers/pcmcia/yenta.c Mon Jun 17 04:49:06 2002
+++ linux-2.5.22-bh/drivers/pcmcia/yenta.c      Mon Jun 17 13:11:16 2002
@@ -6,6 +6,7 @@
#include <linux/init.h>
#include <linux/pci.h>
#include <linux/sched.h>
+#include <linux/tqueue.h>
#include <linux/interrupt.h>
#include <linux/delay.h>
#include <linux/module.h>
diff -urNX dontdiff linux-2.5.22/drivers/s390/char/con3215.c linux-2.5.22-bh/drivers/s390/char/con3215.c
--- linux-2.5.22/drivers/s390/char/con3215.c    Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/char/con3215.c Mon Jun 17 12:11:34 2002
@@ -381,8 +381,7 @@
       raw->tqueue.sync = 0;
        raw->tqueue.routine = raw3215_softint;
        raw->tqueue.data = raw;
-        queue_task(&raw->tqueue, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&raw->tqueue);
}

/*
diff -urNX dontdiff linux-2.5.22/drivers/s390/char/ctrlchar.c linux-2.5.22-bh/drivers/s390/char/ctrlchar.c
--- linux-2.5.22/drivers/s390/char/ctrlchar.c   Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/s390/char/ctrlchar.c        Mon Jun 17 12:12:15 2002
@@ -67,8 +67,7 @@
                       if (len == 3) {
                               ctrlchar_sysrq_key = buf[2];
                               ctrlchar_tq.data = tty;
-                               queue_task(&ctrlchar_tq, &tq_immediate);
-                               mark_bh(IMMEDIATE_BH);
+                               queue_immediate_task(&ctrlchar_tq);
                               return (char *)-1;
                       }
                       break;
diff -urNX dontdiff linux-2.5.22/drivers/s390/char/tapeblock.c linux-2.5.22-bh/drivers/s390/char/tapeblock.c
--- linux-2.5.22/drivers/s390/char/tapeblock.c  Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/char/tapeblock.c       Mon Jun 17 12:11:48 2002
@@ -415,8 +415,7 @@
       td->blk_data.bh_tq.routine = (void *) (void *) run_tapeblock_exec_IO;
       td->blk_data.bh_tq.data = td;

-       queue_task (&td->blk_data.bh_tq, &tq_immediate);
-       mark_bh (IMMEDIATE_BH);
+       queue_immediate_task (&td->blk_data.bh_tq);
       return;
}

diff -urNX dontdiff linux-2.5.22/drivers/s390/char/tubfs.c linux-2.5.22-bh/drivers/s390/char/tubfs.c
--- linux-2.5.22/drivers/s390/char/tubfs.c      Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/char/tubfs.c   Mon Jun 17 12:11:06 2002
@@ -277,8 +277,7 @@
       tubp->flags |= TUB_BHPENDING;
       tubp->tqueue.routine = fs3270_bh;
       tubp->tqueue.data = tubp;
-       queue_task(&tubp->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&tubp->tqueue);
}

/*
diff -urNX dontdiff linux-2.5.22/drivers/s390/char/tubtty.c linux-2.5.22-bh/drivers/s390/char/tubtty.c
--- linux-2.5.22/drivers/s390/char/tubtty.c     Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/char/tubtty.c  Mon Jun 17 12:12:01 2002
@@ -665,8 +665,7 @@
       tubp->flags |= TUB_BHPENDING;
       tubp->tqueue.routine = tty3270_bh;
       tubp->tqueue.data = tubp;
-       queue_task(&tubp->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&tubp->tqueue);
}

/*
diff -urNX dontdiff linux-2.5.22/drivers/s390/net/ctctty.c linux-2.5.22-bh/drivers/s390/net/ctctty.c
--- linux-2.5.22/drivers/s390/net/ctctty.c      Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/net/ctctty.c   Mon Jun 17 12:14:01 2002
@@ -272,8 +272,7 @@
        */
       skb_queue_tail(&info->rx_queue, skb);
       /* Schedule dequeuing */
-       queue_task(&info->tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&info->tq);
}

static int
@@ -390,8 +389,7 @@
       skb_reserve(skb, skb_res);
       *(skb_put(skb, 1)) = c;
       skb_queue_head(&info->tx_queue, skb);
-       queue_task(&info->tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&info->tq);
}

static void
@@ -400,8 +398,7 @@
       if (ctc_tty_shuttingdown)
               return;
       info->flags |= CTC_ASYNC_TX_LINESTAT;
-       queue_task(&info->tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&info->tq);
}

static void
@@ -562,8 +559,7 @@
       }
       if (skb_queue_len(&info->tx_queue)) {
               info->lsr &= ~UART_LSR_TEMT;
-               queue_task(&info->tq, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&info->tq);
       }
       if (from_user)
               up(&info->write_sem);
@@ -628,8 +624,7 @@
               return;
       if (tty->stopped || tty->hw_stopped || (!skb_queue_len(&info->tx_queue)))
               return;
-       queue_task(&info->tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&info->tq);
}

/*
@@ -1182,8 +1177,7 @@
                       info->lsr |= UART_LSR_TEMT;
               again |= ctc_tty_readmodem(info);
               if (again) {
-                       queue_task(&info->tq, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&info->tq);
               }
       }
       spin_unlock_irqrestore(&ctc_tty_lock, saveflags);
diff -urNX dontdiff linux-2.5.22/drivers/s390/net/iucv.c linux-2.5.22-bh/drivers/s390/net/iucv.c
--- linux-2.5.22/drivers/s390/net/iucv.c        Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/net/iucv.c     Mon Jun 17 12:12:31 2002
@@ -2202,8 +2202,7 @@
       spin_unlock(&iucv_irq_queue_lock);

       if (atomic_compare_and_swap (0, 1, &iucv_bh_scheduled) == 0) {
-               queue_task (&iucv_tq, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task (&iucv_tq);
       }

       irq_exit(cpu, 0x4000);
diff -urNX dontdiff linux-2.5.22/drivers/s390/net/lcs.c linux-2.5.22-bh/drivers/s390/net/lcs.c
--- linux-2.5.22/drivers/s390/net/lcs.c Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/drivers/s390/net/lcs.c      Mon Jun 17 12:14:24 2002
@@ -1444,8 +1444,7 @@
        * needing mod usage counts */
       lcs_debug_event(2, "lcs_queue_write write=%p\n", write);
       write->resume_queued = TRUE;
-       queue_task(&write->resume_task, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&write->resume_task);
}

static void
diff -urNX dontdiff linux-2.5.22/drivers/sbus/audio/dmy.c linux-2.5.22-bh/drivers/sbus/audio/dmy.c
--- linux-2.5.22/drivers/sbus/audio/dmy.c       Sun Jun  2 18:44:44 2002
+++ linux-2.5.22-bh/drivers/sbus/audio/dmy.c    Mon Jun 17 12:09:52 2002
@@ -552,8 +552,7 @@
        dummy_chip->tqueue.routine = dummy_output_done_task;
        dummy_chip->tqueue.data = drv;

-        queue_task(&dummy_chip->tqueue, &tq_immediate);
-        mark_bh(IMMEDIATE_BH);
+        queue_immediate_task(&dummy_chip->tqueue);
}

static void dummy_start_input(struct sparcaudio_driver *drv, __u8 * buffer,
diff -urNX dontdiff linux-2.5.22/drivers/sbus/char/aurora.c linux-2.5.22-bh/drivers/sbus/char/aurora.c
--- linux-2.5.22/drivers/sbus/char/aurora.c     Sun Jun  2 18:44:42 2002
+++ linux-2.5.22-bh/drivers/sbus/char/aurora.c  Mon Jun 17 13:03:01 2002
@@ -105,8 +105,6 @@
static struct termios * aurora_termios[AURORA_TNPORTS] = { NULL, };
static struct termios * aurora_termios_locked[AURORA_TNPORTS] = { NULL, };

-DECLARE_TASK_QUEUE(tq_aurora);
-
static inline int aurora_paranoia_check(struct Aurora_port const * port,
                                   kdev_t device, const char *routine)
{
@@ -437,8 +435,7 @@
       printk("aurora_mark_event: start\n");
#endif
       set_bit(event, &port->event);
-       queue_task(&port->tqueue, &tq_aurora);
-       mark_bh(AURORA_BH);
+       queue_immediate_task(&port->tqueue);
#ifdef AURORA_DEBUG
       printk("aurora_mark_event: end\n");
#endif
@@ -2267,11 +2264,6 @@
#endif
}

-static void do_aurora_bh(void)
-{
-        run_task_queue(&tq_aurora);
-}
-
static void do_softint(void *private_)
{
       struct Aurora_port      *port = (struct Aurora_port *) private_;
@@ -2308,7 +2300,6 @@
               printk(KERN_ERR "aurora: Couldn't get free page.\n");
               return 1;
       }
-       init_bh(AURORA_BH, do_aurora_bh);
/*     memset(IRQ_to_board, 0, sizeof(IRQ_to_board));*/
       memset(&aurora_driver, 0, sizeof(aurora_driver));
       aurora_driver.magic = TTY_DRIVER_MAGIC;
diff -urNX dontdiff linux-2.5.22/drivers/sbus/char/sab82532.c linux-2.5.22-bh/drivers/sbus/char/sab82532.c
--- linux-2.5.22/drivers/sbus/char/sab82532.c   Sun Jun  2 18:44:47 2002
+++ linux-2.5.22-bh/drivers/sbus/char/sab82532.c        Mon Jun 17 13:03:23 2002
@@ -42,14 +42,6 @@

#include "sunserial.h"

-static DECLARE_TASK_QUEUE(tq_serial);
-
-/* This is (one of many) a special gross hack to allow SU and
- * SAB serials to co-exist on the same machine. -DaveM
- */
-#undef SERIAL_BH
-#define SERIAL_BH      AURORA_BH
-
static struct tty_driver serial_driver, callout_driver;
static int sab82532_refcount;

@@ -313,8 +305,7 @@
static void sab82532_sched_event(struct sab82532 *info, int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static void receive_chars(struct sab82532 *info,
@@ -654,11 +645,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using sab82532_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct sab82532 *info = (struct sab82532 *)private_;
@@ -2225,8 +2211,6 @@
       if (!sab82532_chain)
               return -ENODEV;

-       init_bh(SERIAL_BH, do_serial_bh);
-
       show_serial_version();

       /* Initialize the tty_driver structure */
@@ -2441,7 +2425,6 @@
       /* printk("Unloading %s: version %s\n", serial_name, serial_version); */
       save_flags(flags);
       cli();
-        remove_bh(SERIAL_BH);
       if ((e1 = tty_unregister_driver(&serial_driver)))
               printk("SERIAL: failed to unregister serial driver (%d)\n",
                      e1);
diff -urNX dontdiff linux-2.5.22/drivers/sbus/char/su.c linux-2.5.22-bh/drivers/sbus/char/su.c
--- linux-2.5.22/drivers/sbus/char/su.c Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/drivers/sbus/char/su.c      Mon Jun 17 13:03:14 2002
@@ -173,8 +173,6 @@
static char *serial_name = "PCIO serial driver";
static char serial_version[16];

-static DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -345,8 +343,7 @@
su_sched_event(struct su_struct *info, int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

static void
@@ -683,11 +680,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using su_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct su_struct        *info = (struct su_struct *) private_;
@@ -2480,7 +2472,6 @@
       int i;
       struct su_struct *info;

-       init_bh(SERIAL_BH, do_serial_bh);
       show_su_version();

       /* Initialize the tty_driver structure */
diff -urNX dontdiff linux-2.5.22/drivers/sbus/char/zs.c linux-2.5.22-bh/drivers/sbus/char/zs.c
--- linux-2.5.22/drivers/sbus/char/zs.c Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/sbus/char/zs.c      Mon Jun 17 13:03:38 2002
@@ -135,8 +135,6 @@

#define ZS_CLOCK         4915200   /* Zilog input clock rate */

-DECLARE_TASK_QUEUE(tq_serial);
-
static struct tty_driver serial_driver, callout_driver;
static int serial_refcount;

@@ -479,8 +477,7 @@
static void zs_sched_event(struct sun_serial *info, int event)
{
       info->event |= 1 << event;
-       queue_task(&info->tqueue, &tq_serial);
-       mark_bh(SERIAL_BH);
+       queue_immediate_task(&info->tqueue);
}

#ifndef __sparc_v9__
@@ -731,11 +728,6 @@
 * interrupt driver proper are done; the interrupt driver schedules
 * them using zs_sched_event(), and they get done here.
 */
-static void do_serial_bh(void)
-{
-       run_task_queue(&tq_serial);
-}
-
static void do_softint(void *private_)
{
       struct sun_serial       *info = (struct sun_serial *) private_;
@@ -2430,9 +2422,6 @@
       unsigned long flags;
       struct sun_serial *info;
       char dummy;
-
-       /* Setup base handler, and timer table. */
-       init_bh(SERIAL_BH, do_serial_bh);

       show_serial_version();

diff -urNX dontdiff linux-2.5.22/drivers/scsi/aha152x.c linux-2.5.22-bh/drivers/scsi/aha152x.c
--- linux-2.5.22/drivers/scsi/aha152x.c Mon Jun 17 04:49:06 2002
+++ linux-2.5.22-bh/drivers/scsi/aha152x.c      Mon Jun 17 12:06:55 2002
@@ -1941,8 +1941,7 @@
       /* Poke the BH handler */
       HOSTDATA(shpnt)->service++;
       aha152x_tq.routine = (void *) run;
-       queue_task(&aha152x_tq, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&aha152x_tq);
}

/*
diff -urNX dontdiff linux-2.5.22/drivers/scsi/atari_NCR5380.c linux-2.5.22-bh/drivers/scsi/atari_NCR5380.c
--- linux-2.5.22/drivers/scsi/atari_NCR5380.c   Sun Jun  2 18:44:51 2002
+++ linux-2.5.22-bh/drivers/scsi/atari_NCR5380.c        Mon Jun 17 12:07:45 2002
@@ -654,8 +654,7 @@
          queue it on the 'immediate' task queue, to be processed
          immediately after the current interrupt processing has
          finished. */
-       queue_task(&NCR5380_tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&NCR5380_tqueue);
    }
    /* else: nothing to do: the running NCR5380_main() will pick up
       any newly queued command. */
diff -urNX dontdiff linux-2.5.22/drivers/scsi/imm.c linux-2.5.22-bh/drivers/scsi/imm.c
--- linux-2.5.22/drivers/scsi/imm.c     Sun Jun  2 18:44:53 2002
+++ linux-2.5.22-bh/drivers/scsi/imm.c  Mon Jun 17 12:09:13 2002
@@ -1105,8 +1105,7 @@

    imm_hosts[host_no].imm_tq.data = imm_hosts + host_no;
    imm_hosts[host_no].imm_tq.sync = 0;
-    queue_task(&imm_hosts[host_no].imm_tq, &tq_immediate);
-    mark_bh(IMMEDIATE_BH);
+    queue_immediate_task(&imm_hosts[host_no].imm_tq);

    return 0;
}
diff -urNX dontdiff linux-2.5.22/drivers/scsi/mac_NCR5380.c linux-2.5.22-bh/drivers/scsi/mac_NCR5380.c
--- linux-2.5.22/drivers/scsi/mac_NCR5380.c     Sun Jun  2 18:44:44 2002
+++ linux-2.5.22-bh/drivers/scsi/mac_NCR5380.c  Mon Jun 17 12:07:28 2002
@@ -672,8 +672,7 @@
          queue it on the 'immediate' task queue, to be processed
          immediately after the current interrupt processing has
          finished. */
-       queue_task(&NCR5380_tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&NCR5380_tqueue);
    }
    /* else: nothing to do: the running NCR5380_main() will pick up
       any newly queued command. */
diff -urNX dontdiff linux-2.5.22/drivers/scsi/oktagon_esp.c linux-2.5.22-bh/drivers/scsi/oktagon_esp.c
--- linux-2.5.22/drivers/scsi/oktagon_esp.c     Sun Jun  2 18:44:40 2002
+++ linux-2.5.22-bh/drivers/scsi/oktagon_esp.c  Mon Jun 17 12:05:48 2002
@@ -516,8 +516,7 @@
       if(dma_on)
        {
         tq_fake_dma.sync = 0;
-         queue_task(&tq_fake_dma,&tq_immediate);
-         mark_bh(IMMEDIATE_BH);
+         queue_immediate_task(&tq_fake_dma);
        }
#else
       while(len && !dma_irq_p(esp))
diff -urNX dontdiff linux-2.5.22/drivers/scsi/ppa.c linux-2.5.22-bh/drivers/scsi/ppa.c
--- linux-2.5.22/drivers/scsi/ppa.c     Sun Jun  2 18:44:39 2002
+++ linux-2.5.22-bh/drivers/scsi/ppa.c  Mon Jun 17 12:05:26 2002
@@ -986,8 +986,7 @@

    ppa_hosts[host_no].ppa_tq.data = ppa_hosts + host_no;
    ppa_hosts[host_no].ppa_tq.sync = 0;
-    queue_task(&ppa_hosts[host_no].ppa_tq, &tq_immediate);
-    mark_bh(IMMEDIATE_BH);
+    queue_immediate_task(&ppa_hosts[host_no].ppa_tq);

    return 0;
}
diff -urNX dontdiff linux-2.5.22/drivers/scsi/scsi.c linux-2.5.22-bh/drivers/scsi/scsi.c
--- linux-2.5.22/drivers/scsi/scsi.c    Mon Jun 17 04:49:06 2002
+++ linux-2.5.22-bh/drivers/scsi/scsi.c Mon Jun 17 04:54:55 2002
@@ -1089,6 +1089,9 @@
       SCSI_LOG_MLQUEUE(3, printk("Leaving scsi_do_cmd()\n"));
}

+void scsi_tasklet_func(unsigned long);
+static DECLARE_TASKLET(scsi_tasklet, scsi_tasklet_func, 0);
+
/*
 * This function is the mid-level interrupt routine, which decides how
 *  to handle error conditions.  Each invocation of this function must
@@ -1186,7 +1189,7 @@
       /*
        * Mark the bottom half handler to be run.
        */
-       mark_bh(SCSI_BH);
+       tasklet_hi_schedule(&scsi_tasklet);
}

/*
@@ -1212,7 +1215,7 @@
 * half queue.  Thus the only time we hold the lock here is when
 * we wish to atomically remove the contents of the queue.
 */
-void scsi_bottom_half_handler(void)
+void scsi_tasklet_func(unsigned long ignore)
{
       Scsi_Cmnd *SCpnt;
       Scsi_Cmnd *SCnext;
@@ -2544,11 +2547,6 @@
        if (scsihosts)
               printk(KERN_INFO "scsi: host order: %s\n", scsihosts);
       scsi_host_no_init (scsihosts);
-       /*
-        * This is where the processing takes place for most everything
-        * when commands are completed.
-        */
-       init_bh(SCSI_BH, scsi_bottom_half_handler);

       return 0;
}
@@ -2558,7 +2556,7 @@
       Scsi_Host_Name *shn, *shn2 = NULL;
       int i;

-       remove_bh(SCSI_BH);
+       tasklet_kill(&scsi_tasklet);

        devfs_unregister (scsi_devfs_handle);
        for (shn = scsi_host_no_list;shn;shn = shn->next) {
diff -urNX dontdiff linux-2.5.22/drivers/scsi/sun3_NCR5380.c linux-2.5.22-bh/drivers/scsi/sun3_NCR5380.c
--- linux-2.5.22/drivers/scsi/sun3_NCR5380.c    Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/scsi/sun3_NCR5380.c Mon Jun 17 12:07:15 2002
@@ -660,8 +660,7 @@
          queue it on the 'immediate' task queue, to be processed
          immediately after the current interrupt processing has
          finished. */
-       queue_task(&NCR5380_tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&NCR5380_tqueue);
    }
    /* else: nothing to do: the running NCR5380_main() will pick up
       any newly queued command. */
diff -urNX dontdiff linux-2.5.22/drivers/usb/class/bluetty.c linux-2.5.22-bh/drivers/usb/class/bluetty.c
--- linux-2.5.22/drivers/usb/class/bluetty.c    Sun Jun  2 18:44:43 2002
+++ linux-2.5.22-bh/drivers/usb/class/bluetty.c Mon Jun 17 12:24:50 2002
@@ -1007,8 +1007,7 @@
       }

       /* wake up our little function to let the tty layer know that something happened */
-       queue_task(&bluetooth->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&bluetooth->tqueue);
       return;
}

diff -urNX dontdiff linux-2.5.22/drivers/usb/class/cdc-acm.c linux-2.5.22-bh/drivers/usb/class/cdc-acm.c
--- linux-2.5.22/drivers/usb/class/cdc-acm.c    Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/usb/class/cdc-acm.c Mon Jun 17 12:24:33 2002
@@ -272,8 +272,7 @@
       if (urb->status)
               dbg("nonzero write bulk status received: %d", urb->status);

-       queue_task(&acm->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&acm->tqueue);
}

static void acm_softint(void *private)
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/cyberjack.c linux-2.5.22-bh/drivers/usb/serial/cyberjack.c
--- linux-2.5.22/drivers/usb/serial/cyberjack.c Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/cyberjack.c      Mon Jun 17 12:24:18 2002
@@ -430,8 +430,7 @@
                       /* Throw away data. No better idea what to do with it. */
                       priv->wrfilled=0;
                       priv->wrsent=0;
-                       queue_task(&port->tqueue, &tq_immediate);
-                       mark_bh(IMMEDIATE_BH);
+                       queue_immediate_task(&port->tqueue);
                       return;
               }

@@ -447,13 +446,11 @@
                       priv->wrsent=0;
               }

-               queue_task(&port->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&port->tqueue);
               return;
       }

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/empeg.c linux-2.5.22-bh/drivers/usb/serial/empeg.c
--- linux-2.5.22/drivers/usb/serial/empeg.c     Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/empeg.c  Mon Jun 17 12:18:01 2002
@@ -359,8 +359,7 @@
               return;
       }

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;

diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/ftdi_sio.c linux-2.5.22-bh/drivers/usb/serial/ftdi_sio.c
--- linux-2.5.22/drivers/usb/serial/ftdi_sio.c  Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/ftdi_sio.c       Mon Jun 17 12:16:50 2002
@@ -477,8 +477,7 @@
               dbg("nonzero write bulk status received: %d", urb->status);
               return;
       }
-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
} /* ftdi_sio_write_bulk_callback */
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/ipaq.c linux-2.5.22-bh/drivers/usb/serial/ipaq.c
--- linux-2.5.22/drivers/usb/serial/ipaq.c      Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/ipaq.c   Mon Jun 17 12:17:07 2002
@@ -446,8 +446,7 @@
               priv->active = 0;
               spin_unlock_irqrestore(&write_list_lock, flags);
       }
-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/ir-usb.c linux-2.5.22-bh/drivers/usb/serial/ir-usb.c
--- linux-2.5.22/drivers/usb/serial/ir-usb.c    Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/ir-usb.c Mon Jun 17 12:18:39 2002
@@ -422,8 +422,7 @@
               urb->actual_length,
               urb->transfer_buffer);

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/keyspan.c linux-2.5.22-bh/drivers/usb/serial/keyspan.c
--- linux-2.5.22/drivers/usb/serial/keyspan.c   Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/drivers/usb/serial/keyspan.c        Mon Jun 17 12:16:32 2002
@@ -447,8 +447,7 @@
       dbg ("%s - urb %d", __FUNCTION__, urb == p_priv->out_urbs[1]);

       if (port->open_count) {
-               queue_task(&port->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&port->tqueue);
       }
}

diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/kl5kusb105.c linux-2.5.22-bh/drivers/usb/serial/kl5kusb105.c
--- linux-2.5.22/drivers/usb/serial/kl5kusb105.c        Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/kl5kusb105.c     Mon Jun 17 12:18:58 2002
@@ -576,8 +576,7 @@
       }

       /* from generic_write_bulk_callback */
-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
} /* klsi_105_write_bulk_completion_callback */
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/mct_u232.c linux-2.5.22-bh/drivers/usb/serial/mct_u232.c
--- linux-2.5.22/drivers/usb/serial/mct_u232.c  Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/mct_u232.c       Mon Jun 17 12:21:22 2002
@@ -502,8 +502,7 @@

       } else {
               /* from generic_write_bulk_callback */
-               queue_task(&port->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&port->tqueue);
       }

       return;
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/omninet.c linux-2.5.22-bh/drivers/usb/serial/omninet.c
--- linux-2.5.22/drivers/usb/serial/omninet.c   Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/omninet.c        Mon Jun 17 12:17:37 2002
@@ -352,8 +352,7 @@
               return;
       }

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

//     dbg("omninet_write_bulk_callback, tty %0x\n", tty);

diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/pl2303.c linux-2.5.22-bh/drivers/usb/serial/pl2303.c
--- linux-2.5.22/drivers/usb/serial/pl2303.c    Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/pl2303.c Mon Jun 17 12:18:24 2002
@@ -697,8 +697,7 @@
               return;
       }

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/usbserial.c linux-2.5.22-bh/drivers/usb/serial/usbserial.c
--- linux-2.5.22/drivers/usb/serial/usbserial.c Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/usbserial.c      Mon Jun 17 12:17:50 2002
@@ -1101,8 +1101,7 @@
               return;
       }

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/drivers/usb/serial/visor.c linux-2.5.22-bh/drivers/usb/serial/visor.c
--- linux-2.5.22/drivers/usb/serial/visor.c     Mon Jun 17 04:49:07 2002
+++ linux-2.5.22-bh/drivers/usb/serial/visor.c  Mon Jun 17 12:17:22 2002
@@ -453,8 +453,7 @@
       /* free up the transfer buffer, as usb_free_urb() does not do this */
       kfree (urb->transfer_buffer);

-       queue_task(&port->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&port->tqueue);

       return;
}
diff -urNX dontdiff linux-2.5.22/include/asm-s390/qdio.h linux-2.5.22-bh/include/asm-s390/qdio.h
--- linux-2.5.22/include/asm-s390/qdio.h        Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/include/asm-s390/qdio.h     Mon Jun 17 07:25:31 2002
@@ -82,8 +82,6 @@
#define QDIO_CLEANUP_CLEAR_TIMEOUT 20000
#define QDIO_CLEANUP_HALT_TIMEOUT 10000

-#define QDIO_BH AURORA_BH
-
#define QDIO_IRQ_BUCKETS 256 /* heavy..., but does only use a few bytes, but
                             be rather faster in cases of collisions
                             (if there really is a collision, it is
diff -urNX dontdiff linux-2.5.22/include/asm-s390x/qdio.h linux-2.5.22-bh/include/asm-s390x/qdio.h
--- linux-2.5.22/include/asm-s390x/qdio.h       Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/include/asm-s390x/qdio.h    Mon Jun 17 07:25:22 2002
@@ -83,8 +83,6 @@
#define QDIO_CLEANUP_CLEAR_TIMEOUT 20000
#define QDIO_CLEANUP_HALT_TIMEOUT 10000

-#define QDIO_BH AURORA_BH
-
#define QDIO_IRQ_BUCKETS 256 /* heavy..., but does only use a few bytes, but
                             be rather faster in cases of collisions
                             (if there really is a collision, it is
diff -urNX dontdiff linux-2.5.22/include/linux/interrupt.h linux-2.5.22-bh/include/linux/interrupt.h
--- linux-2.5.22/include/linux/interrupt.h      Thu Jun  6 06:57:51 2002
+++ linux-2.5.22-bh/include/linux/interrupt.h   Mon Jun 17 13:22:41 2002
@@ -22,28 +22,6 @@
       struct irqaction *next;
};

-
-/* Who gets which entry in bh_base.  Things which will occur most often
-   should come first */
-
-enum {
-       TIMER_BH = 0,
-       TQUEUE_BH,
-       DIGI_BH,
-       SERIAL_BH,
-       RISCOM8_BH,
-       SPECIALIX_BH,
-       AURORA_BH,
-       ESP_BH,
-       SCSI_BH,
-       IMMEDIATE_BH,
-       CYCLADES_BH,
-       CM206_BH,
-       JS_BH,
-       MACSERIAL_BH,
-       ISICOM_BH
-};
-
#include <asm/hardirq.h>
#include <asm/softirq.h>

@@ -117,6 +95,7 @@
#define DECLARE_TASKLET_DISABLED(name, func, data) \
struct tasklet_struct name = { NULL, 0, ATOMIC_INIT(1), func, data }

+extern struct tasklet_struct immediate_tasklet;

enum
{
@@ -209,22 +188,6 @@
#define SMP_TIMER_DEFINE(name, task)

#endif /* CONFIG_SMP */
-
-
-/* Old BH definitions */
-
-extern struct tasklet_struct bh_task_vec[];
-
-/* It is exported _ONLY_ for wait_on_irq(). */
-extern spinlock_t global_bh_lock;
-
-static inline void mark_bh(int nr)
-{
-       tasklet_hi_schedule(bh_task_vec+nr);
-}
-
-extern void init_bh(int nr, void (*routine)(void));
-extern void remove_bh(int nr);


/*
diff -urNX dontdiff linux-2.5.22/include/linux/sched.h linux-2.5.22-bh/include/linux/sched.h
--- linux-2.5.22/include/linux/sched.h  Mon Jun 17 04:49:09 2002
+++ linux-2.5.22-bh/include/linux/sched.h       Mon Jun 17 12:49:29 2002
@@ -7,7 +7,6 @@

#include <linux/config.h>
#include <linux/capability.h>
-#include <linux/tqueue.h>
#include <linux/threads.h>
#include <linux/kernel.h>
#include <linux/types.h>
@@ -160,7 +159,6 @@
extern signed long FASTCALL(schedule_timeout(signed long timeout));
asmlinkage void schedule(void);

-extern int schedule_task(struct tq_struct *task);
extern void flush_scheduled_tasks(void);
extern int start_context_thread(void);
extern int current_is_keventd(void);
diff -urNX dontdiff linux-2.5.22/include/linux/tqueue.h linux-2.5.22-bh/include/linux/tqueue.h
--- linux-2.5.22/include/linux/tqueue.h Thu Jun  6 06:57:51 2002
+++ linux-2.5.22-bh/include/linux/tqueue.h      Mon Jun 17 12:50:29 2002
@@ -16,6 +16,7 @@
#include <linux/spinlock.h>
#include <linux/list.h>
#include <linux/bitops.h>
+#include <linux/interrupt.h>
#include <asm/system.h>

/*
@@ -109,6 +110,15 @@
       }
       return ret;
}
+
+static inline void queue_immediate_task(struct tq_struct *tq)
+{
+       queue_task(tq, &tq_immediate);
+       tasklet_schedule(&immediate_tasklet);
+}
+
+/* Schedule a tq to run in process context */
+extern int schedule_task(struct tq_struct *task);

/*
 * Call all "bottom halfs" on a given list.
diff -urNX dontdiff linux-2.5.22/kernel/context.c linux-2.5.22-bh/kernel/context.c
--- linux-2.5.22/kernel/context.c       Sun Jun  2 18:44:47 2002
+++ linux-2.5.22-bh/kernel/context.c    Mon Jun 17 12:53:16 2002
@@ -20,6 +20,7 @@
#include <linux/unistd.h>
#include <linux/signal.h>
#include <linux/completion.h>
+#include <linux/tqueue.h>

static DECLARE_TASK_QUEUE(tq_context);
static DECLARE_WAIT_QUEUE_HEAD(context_task_wq);
diff -urNX dontdiff linux-2.5.22/kernel/kmod.c linux-2.5.22-bh/kernel/kmod.c
--- linux-2.5.22/kernel/kmod.c  Sun Jun  2 18:44:45 2002
+++ linux-2.5.22-bh/kernel/kmod.c       Mon Jun 17 12:52:57 2002
@@ -28,6 +28,7 @@
#include <linux/namespace.h>
#include <linux/completion.h>
#include <linux/file.h>
+#include <linux/tqueue.h>

#include <asm/uaccess.h>

diff -urNX dontdiff linux-2.5.22/kernel/sched.c linux-2.5.22-bh/kernel/sched.c
--- linux-2.5.22/kernel/sched.c Mon Jun 17 04:49:11 2002
+++ linux-2.5.22-bh/kernel/sched.c      Mon Jun 17 04:55:10 2002
@@ -1634,8 +1634,6 @@

extern void init_timervecs(void);
extern void timer_bh(void);
-extern void tqueue_bh(void);
-extern void immediate_bh(void);

void __init sched_init(void)
{
@@ -1672,8 +1670,6 @@

       init_timervecs();
       init_bh(TIMER_BH, timer_bh);
-       init_bh(TQUEUE_BH, tqueue_bh);
-       init_bh(IMMEDIATE_BH, immediate_bh);

       /*
        * The boot idle thread does lazy MMU switching as well:
diff -urNX dontdiff linux-2.5.22/kernel/softirq.c linux-2.5.22-bh/kernel/softirq.c
--- linux-2.5.22/kernel/softirq.c       Sun Jun  2 18:44:44 2002
+++ linux-2.5.22-bh/kernel/softirq.c    Mon Jun 17 13:26:26 2002
@@ -7,6 +7,8 @@
 * due bh_mask_count not atomic handling. Copyright (C) 1998  Andrea Arcangeli
 *
 * Rewritten. Old one was good in 2.2, but in 2.3 it was immoral. --ANK (990903)
+ *
+ * Bottom halves finally killed by Matthew Wilcox in 2002.
 */

#include <linux/config.h>
@@ -272,68 +274,13 @@



-/* Old style BHs */
-
-static void (*bh_base[32])(void);
-struct tasklet_struct bh_task_vec[32];
-
-/* BHs are serialized by spinlock global_bh_lock.
-
-   It is still possible to make synchronize_bh() as
-   spin_unlock_wait(&global_bh_lock). This operation is not used
-   by kernel now, so that this lock is not made private only
-   due to wait_on_irq().
-
-   It can be removed only after auditing all the BHs.
- */
-spinlock_t global_bh_lock = SPIN_LOCK_UNLOCKED;
-
-static void bh_action(unsigned long nr)
-{
-       int cpu = smp_processor_id();
-
-       if (!spin_trylock(&global_bh_lock))
-               goto resched;
-
-       if (!hardirq_trylock(cpu))
-               goto resched_unlock;
-
-       if (bh_base[nr])
-               bh_base[nr]();
-
-       hardirq_endlock(cpu);
-       spin_unlock(&global_bh_lock);
-       return;
-
-resched_unlock:
-       spin_unlock(&global_bh_lock);
-resched:
-       mark_bh(nr);
-}
-
-void init_bh(int nr, void (*routine)(void))
-{
-       bh_base[nr] = routine;
-       mb();
-}
-
-void remove_bh(int nr)
-{
-       tasklet_kill(bh_task_vec+nr);
-       bh_base[nr] = NULL;
-}
-
void __init softirq_init()
{
-       int i;
-
-       for (i=0; i<32; i++)
-               tasklet_init(bh_task_vec+i, bh_action, i);
-
       open_softirq(TASKLET_SOFTIRQ, tasklet_action, NULL);
       open_softirq(HI_SOFTIRQ, tasklet_hi_action, NULL);
}

+/* Invoke every task on a queue */
void __run_task_queue(task_queue *list)
{
       struct list_head head, *next;
diff -urNX dontdiff linux-2.5.22/kernel/sys.c linux-2.5.22-bh/kernel/sys.c
--- linux-2.5.22/kernel/sys.c   Sun Jun  2 18:44:41 2002
+++ linux-2.5.22-bh/kernel/sys.c        Mon Jun 17 12:52:35 2002
@@ -16,6 +16,7 @@
#include <linux/init.h>
#include <linux/highuid.h>
#include <linux/fs.h>
+#include <linux/tqueue.h>
#include <linux/device.h>

#include <asm/uaccess.h>
diff -urNX dontdiff linux-2.5.22/kernel/timer.c linux-2.5.22-bh/kernel/timer.c
--- linux-2.5.22/kernel/timer.c Sun Jun  9 06:09:49 2002
+++ linux-2.5.22-bh/kernel/timer.c      Mon Jun 17 12:52:09 2002
@@ -22,6 +22,7 @@
#include <linux/delay.h>
#include <linux/smp_lock.h>
#include <linux/interrupt.h>
+#include <linux/tqueue.h>
#include <linux/kernel_stat.h>

#include <asm/uaccess.h>
@@ -333,16 +334,20 @@

spinlock_t tqueue_lock = SPIN_LOCK_UNLOCKED;

-void tqueue_bh(void)
+static void tqueue_tasklet_func(unsigned long ignore)
{
       run_task_queue(&tq_timer);
}

-void immediate_bh(void)
+static DECLARE_TASKLET(tqueue_tasklet, tqueue_tasklet_func, 0);
+
+static void immediate_tasklet_func(unsigned long ignore)
{
       run_task_queue(&tq_immediate);
}

+DECLARE_TASKLET(immediate_tasklet, immediate_tasklet_func, 0);
+
/*
 * this routine handles the overflow of the microsecond field
 *
@@ -677,7 +682,7 @@
#endif
       mark_bh(TIMER_BH);
       if (TQ_ACTIVE(tq_timer))
-               mark_bh(TQUEUE_BH);
+               tasklet_schedule(&tqueue_tasklet);
}

#if !defined(__alpha__) && !defined(__ia64__)
diff -urNX dontdiff linux-2.5.22/net/irda/ircomm/ircomm_param.c linux-2.5.22-bh/net/irda/ircomm/ircomm_param.c
--- linux-2.5.22/net/irda/ircomm/ircomm_param.c Sun Jun  2 18:44:49 2002
+++ linux-2.5.22-bh/net/irda/ircomm/ircomm_param.c      Mon Jun 17 12:32:27 2002
@@ -164,8 +164,7 @@

       if (flush) {
               /* ircomm_tty_do_softint will take care of the rest */
-               queue_task(&self->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&self->tqueue);
       }

       return count;
diff -urNX dontdiff linux-2.5.22/net/irda/ircomm/ircomm_tty.c linux-2.5.22-bh/net/irda/ircomm/ircomm_tty.c
--- linux-2.5.22/net/irda/ircomm/ircomm_tty.c   Mon Jun 17 04:49:11 2002
+++ linux-2.5.22-bh/net/irda/ircomm/ircomm_tty.c        Mon Jun 17 12:31:19 2002
@@ -619,8 +619,7 @@
        * Let do_softint() do this to avoid race condition with
        * do_softint() ;-)
        */
-       queue_task(&self->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&self->tqueue);
}

/*
@@ -796,8 +795,7 @@
        * its 256 byte tx buffer). We will then defragment and send out
        * all this data as one single packet.
        */
-       queue_task(&self->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&self->tqueue);

       return len;
}
@@ -1120,8 +1118,7 @@
                               /* Wake up processes blocked on open */
                               wake_up_interruptible(&self->open_wait);

-                               queue_task(&self->tqueue, &tq_immediate);
-                               mark_bh(IMMEDIATE_BH);
+                               queue_immediate_task(&self->tqueue);
                               return;
                       }
               } else {
@@ -1234,8 +1231,7 @@
               tty->hw_stopped = 0;

               /* ircomm_tty_do_softint will take care of the rest */
-               queue_task(&self->tqueue, &tq_immediate);
-               mark_bh(IMMEDIATE_BH);
+               queue_immediate_task(&self->tqueue);
               break;
       default:  /* If we get here, something is very wrong, better stop */
       case FLOW_STOP:
diff -urNX dontdiff linux-2.5.22/net/irda/ircomm/ircomm_tty_attach.c linux-2.5.22-bh/net/irda/ircomm/ircomm_tty_attach.c
--- linux-2.5.22/net/irda/ircomm/ircomm_tty_attach.c    Sun Jun  2 18:44:47 2002
+++ linux-2.5.22-bh/net/irda/ircomm/ircomm_tty_attach.c Mon Jun 17 12:32:01 2002
@@ -533,8 +533,7 @@
               wake_up_interruptible(&self->open_wait);
       }

-       queue_task(&self->tqueue, &tq_immediate);
-       mark_bh(IMMEDIATE_BH);
+       queue_immediate_task(&self->tqueue);
}

/*