Reputation: 61
I am trying to implement my own new schedule()
. I want to debug my code.
Can I use printk
function in sched.c
?
I used printk
but it doesn't work. What did I miss?
Upvotes: 6
Views: 2822
Reputation: 9736
Try trace_printk()
.
printk()
has too much of an overhead and schedule()
gets called again before previous printk()
calls finish. This creates a live lock.
Here is a good article about it: https://lwn.net/Articles/365835/
Upvotes: 2
Reputation: 61
It's not safe to call printk while holding the runqueue lock. A special function printk_sched
was introduced in order to have a mechanism to use printk when holding the runqueue lock (https://lkml.org/lkml/2012/3/13/13). Unfortunatly it can just print one message within a tick (and there cannot be more than one tick when holding the run queue lock because interrupts are disabled). This is because an internal buffer is used to save the message.
You can either use lttng2 for logging to user space or patch the implementation of printk_sched
to use a statically allocated pool of buffers that can be used within a tick.
Upvotes: 2
Reputation: 23268
Do you know how often schedule()
is called? It's probably called faster than your computer can flush the print buffer to the log. I would suggest using another method of debugging. For instance running your kernel in QEMU and using remote GDB by loading the kernel.syms file as a symbol table and setting a breakpoint. Other virtualization software offers similar features. Or do it the manual way and walk through your code. Using printk in interrupt handlers is typically a bad idea (unless you're about to panic or stall).
If the error you are seeing doesn't happen often think of using BUG()
or BUG_ON(cond)
instead. These do conditional error messages and shouldn't happen as often as a non-conditional printk
Editing the schedule()
function itself is typically a bad idea (unless you want to support multiple run queue's etc...). It's much better and easier to instead modify a scheduler class. Look at the code of the CFS scheduler to do this. If you want to accomplish something else I can give better advice.
Upvotes: 8
Reputation: 40982
It depends, basically it should be work fine.
try to use dmesg
in shell to trace your printk
if it is not there you apparently didn't invoked it.
2396 if (p->mm && printk_ratelimit()) {
2397 printk(KERN_INFO "process %d (%s) no longer affine to cpu%d\n",
2398 task_pid_nr(p), p->comm, cpu);
2399 }
2400
2401 return dest_cpu;
2402 }
there is a sections in sched.c
that printk
doesn't work e.g.
1660 static int double_lock_balance(struct rq *this_rq, struct rq *busiest)
1661 {
1662 if (unlikely(!irqs_disabled())) {
1663 /* printk() doesn't work good under rq->lock */
1664 raw_spin_unlock(&this_rq->lock);
1665 BUG_ON(1);
1666 }
1667
1668 return _double_lock_balance(this_rq, busiest);
1669 }
you may try to printk
once in 1000 times instead of each time.
Upvotes: 0