Greeting I've got a kernel module that contains something like this: while(loop) { take semaphore A do some I/O on the PCI bus give semaphore A } This loop is launched by a worker thread Meanwhile, I've got write() mapped into a module function like this: my_write() { take semaphore A write to the PCI pus give semaphore A } The problem is that my_write() can never get the A semaphore. The loop is too tight perhaps. Or maybe the system call has a lower priority than the kernel's worker thread. Other than using flags, is there some easy way to fix this? TIA&Cheers
On Sunday 19 March 2006 21:36, Pierre Patino wrote:
Greeting
I've got a kernel module that contains something like this:
while(loop) {
take semaphore A
do some I/O on the PCI bus
give semaphore A
}
So between the give and the take there are basically two instructions, one cmp and one jne, and in those two you expect the kernel to give execution to something else that wants the semaphore I think you need to put a sleep, or a shed_yield or something in there, otherwise odds are your loop is going to hold that semaphore forever -- Certified: Yes. Certifiable: of course! jabber ID: anders@rydsbo.net
Anders Johansson wrote:
On Sunday 19 March 2006 21:36, Pierre Patino wrote:
Greeting
I've got a kernel module that contains something like this:
while(loop) {
take semaphore A
do some I/O on the PCI bus
give semaphore A
}
So between the give and the take there are basically two instructions, one cmp and one jne, and in those two you expect the kernel to give execution to something else that wants the semaphore
I think you need to put a sleep, or a shed_yield or something in there, otherwise odds are your loop is going to hold that semaphore forever
Thanks to Anders and Per for your suggestions. The loop is not as tight as shown but I think I should add the shed_yield() as suggested. Between the take semaphore A and give semaphore A there are dozens of line of code and as well as interrupt-driven event-waits which take about 10ms in total. After the give semaphore there are about a dozen more lines of code but perhaps a sched_yield() is in order. I'll try this Monday. Thanks again
Pierre Patino wrote:
The problem is that my_write() can never get the A semaphore. The loop is too tight perhaps. Or maybe the system call has a lower priority than the kernel's worker thread. Other than using flags, is there some easy way to fix this?
You need to have both of your threads give up control of the CPU - do some IO for instance (through the OS, not direct). Or explicitly give up control with sched_yield(). Finally - I'm not sure, but doesn't the recent kernels have pre-emptive scheduling? Also, if you're on an SMP-machine doing direct(ish) IO, why not just spin-lock? /Per Jessen, Zurich
participants (3)
-
Anders Johansson
-
Per Jessen
-
Pierre Patino