0

hello.ko次の関数でカーネル スレッドを生成するという名前のテスト カーネル モジュールを作成しました。

static int thread_fn(void *data)
{
    while(1)
    {
        printk(KERN_INFO "thread is running....\n");
        ssleep(5);

        printk(KERN_INFO "checking if I need to stop\n");
        if(kthread_should_stop())
            break;
    }
    printk(KERN_INFO "thread exiting\n");
    return 0;
}

static int __init hello_init(void)
{
    printk(KERN_INFO "This is from init \n");
    mythread = kthread_create(thread_fn, NULL, "mythread");
    if(!mythread)
    {
        printk(KERN_ERR "Thread creation failed\n");
        return 1;
    }
    else
    {
        printk(KERN_INFO "Thread created successfully.\n");
        //thread is not running yet. Its in sleep state.
    }
    //bind to CPU 1
    kthread_bind(mythread,2);
    //start the thread
    wake_up_process(mythread);
    return 0;
}

static void __exit hello_exit(void)
{
    int rc;
    printk(KERN_INFO "This is from exit \n");
    rc = kthread_stop(mythread);
    if(rc)
        printk(KERN_ERR "kthread stop failed\n");
}

module_init(hello_init);
module_exit(hello_exit);

ここで、ftrace を介してこの関数をトレースしたいと思います。したがって、モジュールがロードされるとシンボルが使用可能になることがわかります。

/sys/kernel/debug/tracing # cat available_filter_functions  | grep thread_fn
smpboot_thread_fn
irq_thread_fn
irq_forced_thread_fn
thread_fn [hello]  <<<< my module's function that is to be traced

この関数をフィルタリングするように設定し、トレースをオンにしましたがthread_fn、関数が呼び出されたことを示す dmesg ログを取得しているにもかかわらず、トレースには何も表示されません。

/sys/kernel/debug/tracing # cat set_ftrace_filter
thread_fn [hello]
/sys/kernel/debug/tracing # cat set_graph_function
thread_fn [hello]
/sys/kernel/debug/tracing # cat tracing_on
1
/sys/kernel/debug/tracing # cat current_tracer
function_graph
/sys/kernel/debug/tracing # cat trace
# tracer: function_graph
#
# CPU  DURATION                  FUNCTION CALLS
# |     |   |                     |   |   |   |
/sys/kernel/debug/tracing #

トレースでは何も得られませんが、以下は、dmesgトレースしようとしている同じ関数から繰り返し取得しているログです。

[  856.633370] thread is running....
[  861.752050] checking if I need to stop
[  861.752476] thread is running....
[  866.872571] checking if I need to stop
[  866.872978] thread is running....
[  871.992339] checking if I need to stop
[  871.992821] thread is running....
[  877.113347] checking if I need to stop
[  877.113712] thread is running....
[  882.232438] checking if I need to stop

私のカーネルのバージョンは5.8.0で、これを実行していますqemu-aarch64 version 2.11.1(Debian 1:2.11+dfsg-1ubuntu7.37~cloud0)

私はここで愚かなことをしていますか?それとも、既知の問題にぶつかっていますか?

編集 rootfs として Buildroot を使用しています。trace-cmd今回は、ftrace を直接操作する代わりに使用しました。モジュールをロードし、dmesg上記のように からログを確認できますthread_fn

trace-cmd record -p function_graph -l thread_fn

しかし、私は再び何も得られませんでした。

編集 @IanAbbott コメントから間違いに気付いた後、コードを少し修正して、トレースがアクティブなときに少なくともトレースされている関数が呼び出されるようにしました (エントリ/出口がなく、数行しかなかった以前のケースの代わりに)トレースがアクティブな間、ループで実行されます)。

void hello_log(void)
{
    printk(KERN_INFO "should I stop\n");
}
EXPORT_SYMBOL(hello_log);

static int thread_fn(void *data)
{
    while(1)
    {
        printk(KERN_INFO "thread is running....\n");
        ssleep(5);

        hello_log();
        if(kthread_should_stop())
            break;
    }
    printk(KERN_INFO "thread exiting\n");
    return 0;
}

今、hello_log関数からトレースを取得することを期待していましたが、トレースで何も取得しません。今何が問題なのですか?

4

0 に答える 0