[PATCH] do_bottom_half type routines in modules

pwhiting@fury.ittc.ukans.edu
Mon, 3 May 1999 15:28:29 -0500


Attached below is a simple patch for x86 systems to modify the
kernel's handling of bottom halves. All this patch provides is a
mechanism to switch in a new "bottom halves handler" to replace
do_bottom_half via a module. To accomplish this I add a new function
pointer, bh_handler, which is initialized to point to do_bottom_half.
If your module wants to provide a different behavior then it can
replace that pointer with a pointer to your own routine. One needs to
be careful with this entire process, as bottom halves happen to be
relatively important...

The trivial mod would have been to stub do_bottom_half to simply call
bh_handler, and then move the current do_bottom_half to some other
name. However, a function who's only purpose is to call another
function seemed ugly. So, I modified kernel/sched.c and
arch/i386/kernel/irq.c to call (bh_handler)() instead of
do_bottom_half. If this patch is considered generally useful then
someone would need to make similar changes to the other architectures.
(Not making the change to a specific architecture isn't catastrophic,
it just makes the patch not very useful as do_bottom_half rarely gets
called from the scheduler.)

What good is it? I am not sure it is interesting to anyone but me,
but I have played with a few bottom half handlers that each behave a
little differently. One has a hard limit on how long it will run
before it returns (in this case it is running as a kernel thread so
after it yields it eventually gets rescheduled to finish up - the
bh_handler simply wakes the kernel thread up.) One I would like to
play with is changing the bottom half handler to isolate the work to
be done for the network bottom half and treat it differently. I could
do a quick demux on the incoming packet (ignoring fragments for now)
and possibly associate some them with a process (or, more easily with
a port). If this works the next step might be to give special
priority and possibly even dedicated backlog queues to certain
processes (or ports). Modifying a server that is primarily
acting as a web server to favor port 80 might be useful.

Making the bottom halves handler a function pointer allows all of the
changes to exist within a module instead of having to rebuild the entire
kernel. Of course, it allows to you more easily toast your system as
well.

pete

this patch is against 2.2.7.

diff -ur linux-2.2.7.clean/arch/i386/kernel/irq.c linux/arch/i386/kernel/irq.c
--- linux-2.2.7.clean/arch/i386/kernel/irq.c Mon May 3 14:11:07 1999
+++ linux/arch/i386/kernel/irq.c Mon May 3 14:02:12 1999
@@ -813,7 +813,7 @@
*/
if (1) {
if (bh_active & bh_mask)
- do_bottom_half();
+ (bh_handler)();
}
}

diff -ur linux-2.2.7.clean/include/linux/interrupt.h linux/include/linux/interrupt.h
--- linux-2.2.7.clean/include/linux/interrupt.h Mon May 3 14:11:18 1999
+++ linux/include/linux/interrupt.h Mon May 3 14:01:26 1999
@@ -21,6 +21,7 @@
extern unsigned long bh_active;
extern unsigned long bh_mask;
extern void (*bh_base[32])(void);
+extern void (*bh_handler)(void);

asmlinkage void do_bottom_half(void);

diff -ur linux-2.2.7.clean/kernel/ksyms.c linux/kernel/ksyms.c
--- linux-2.2.7.clean/kernel/ksyms.c Mon May 3 14:10:55 1999
+++ linux/kernel/ksyms.c Mon May 3 14:02:38 1999
@@ -398,3 +398,9 @@

/* library functions */
EXPORT_SYMBOL(strnicmp);
+
+/* bottom half handler */
+EXPORT_SYMBOL(bh_handler);
+EXPORT_SYMBOL(do_bottom_half);
+extern asmlinkage int sys_sched_yield(void);
+EXPORT_SYMBOL(sys_sched_yield);
diff -ur linux-2.2.7.clean/kernel/sched.c linux/kernel/sched.c
--- linux-2.2.7.clean/kernel/sched.c Mon May 3 14:10:44 1999
+++ linux/kernel/sched.c Mon May 3 14:02:27 1999
@@ -58,6 +58,8 @@
DECLARE_TASK_QUEUE(tq_immediate);
DECLARE_TASK_QUEUE(tq_scheduler);

+void (*bh_handler)(void)=&do_bottom_half;
+
/*
* phase-lock loop variables
*/
@@ -665,7 +667,7 @@

/* Do "administrative" work here while we don't hold any locks */
if (bh_active & bh_mask)
- do_bottom_half();
+ (bh_handler)();

spin_lock(&scheduler_lock);
spin_lock_irq(&runqueue_lock);

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/