A little discussion before the question. Linux 2.4 kernel is non preemtive, so if there is a need for context-switch when we are proccecing a system call in the kernel mode, we only do set_need_resched to raise a flag and then when we go back to user mode, we check the flag and do context-switch.
Lets compare this to linux 2.6 which has preemptive kernel. We can't just take kernel of 2.4 and change the set_need_resched (raising flag) to schedule() (directive execution of rescheduling), so in linux kernel 2.6 there is a counter preempt_count, which increases every time on spin_lock() and decreases on spin_unlock().
Actually, this field "preempt_count" determine if the kernel can be preempted. For example on a returning from clock interrupt, if the condition:
(current->need_resched == 1) && (current->preempt_count == 0)
is true, then the kernel executes context-switch.
The Question is why the kernel of linux 2.6 prevents preemption when a lock of type spinlock is held.
What is the scenario that could happen if the kernel didn't prevent the preemption ? Can you give me a concrete example as much detailed as you can ?
Thank you.