/ / linuxでタイマーを使ってカーネルスレッドを停止する - linux、timer、kernel、linux-device-driver

linuxでタイマーを使ってカーネルスレッドを停止する - linux、timer、kernel、linux-device-driver

私は呼び出してカーネルスレッドを停止しようとしていますkthread_stop()はtimerによって呼び出される関数の中にあります。このモジュールをカーネルにロードすると、kthreadはタイマーに記述された指定時間後に開始および停止しますが、ログには何らかのエラーメッセージが表示されます。

誰かが私がこの問題を解決するのを助けることができますか?私はカーネルスレッドプログラミングの初心者です。これは私のコードです

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/timer.h>
#include <linux/kthread.h>
#include <linux/sched.h>
MODULE_LICENSE("GPL");
struct task_struct *task;
static struct timer_list my_timer;
int thread_function(void *data) {
printk(KERN_ALERT"IN THREAD FUNCTION");
while(!kthread_should_stop()){
schedule();
}
printk(KERN_ALERT"after schedulen");
return 1;
}

void my_timer_callback( unsigned long data ){
printk( "my_timer_callback called (%ld).n", jiffies );
printk(KERN_ALERT"THREAD STOPPEDn");
kthread_stop(task);
}

int init_module( void ){
int ret;
printk("Timer module installingn");

//my_timer.function, my_timer.data
setup_timer( &my_timer, my_timer_callback, 0 );

printk( "Starting timer to fire in 2000ms (%ld)n", jiffies );
ret = mod_timer( &my_timer, jiffies + msecs_to_jiffies(2000) );
if (ret) printk("Error in mod_timern");
printk(KERN_INFO"-------------------- THREAD START------------------------");

task = kthread_run(thread_function,NULL,"kerneltthread");
printk(KERN_ALERT"Kernel Thread Name: %sn",task->comm);

return 0;
}

void cleanup_module( void ){
int ret;

ret = del_timer( &my_timer );
if (ret) printk("The timer is still in use...n");

printk("Timer module uninstallingn");

return;
}

MODULE_LICENSE("GPL");

これはログの出力メッセージです

Aug  5 16:35:31 brao kernel: Timer module installing
Aug  5 16:35:31 brao kernel: Starting timer to fire in 2000ms (4299209850)
Aug  5 16:35:31 brao kernel: -------------------- THREAD             START------------------------
Aug  5 16:35:31 brao kernel: Kernel Thread Name: kerneltthread
Aug  5 16:35:31 brao kernel: IN THREAD FUNCTION
Aug  5 16:35:33 brao kernel: my_timer_callback called (4299211856).
Aug  5 16:35:33 brao kernel: THREAD STOPPED
Aug  5 16:35:33 brao kernel: BUG: scheduling while atomic: swapper/3/0/0x10000100
Aug  5 16:35:33 brao kernel: after schedule

回答:

回答№1は1

タイマーの機能 softirqコンテキストで実行されます。 すべきではない。しかしあなたの my_timer_callback コール kthread_stop 関数 待つ kthreadが終了するまで、それは睡眠です。

そう、 scheduling while atomic BUGが発生します。関数は、原子コンテキストのためにそれを行うべきではありませんが、スリープします。