The eval_map_work_func() function, though queued in eval_map_wq,
holds the trace_event_sem read-write lock for a long time during
kernel boot. This causes blocking issues for other functions.

Rename eval_map_wq to trace_init_wq and export it, thereby allowing
other modules to schedule work on this queue asynchronously and
avoiding blockage of the main boot thread.

Signed-off-by: Yaxiong Tian <[email protected]>
---
 kernel/trace/trace.c | 18 +++++++++---------
 kernel/trace/trace.h |  2 ++
 2 files changed, 11 insertions(+), 9 deletions(-)

diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c
index e18005807395..c61e30cb7339 100644
--- a/kernel/trace/trace.c
+++ b/kernel/trace/trace.c
@@ -10774,7 +10774,7 @@ int tracing_init_dentry(void)
 extern struct trace_eval_map *__start_ftrace_eval_maps[];
 extern struct trace_eval_map *__stop_ftrace_eval_maps[];
 
-static struct workqueue_struct *eval_map_wq __initdata;
+struct workqueue_struct *trace_init_wq __initdata;
 static struct work_struct eval_map_work __initdata;
 static struct work_struct tracerfs_init_work __initdata;
 
@@ -10790,15 +10790,15 @@ static int __init trace_eval_init(void)
 {
        INIT_WORK(&eval_map_work, eval_map_work_func);
 
-       eval_map_wq = alloc_workqueue("eval_map_wq", WQ_UNBOUND, 0);
-       if (!eval_map_wq) {
-               pr_err("Unable to allocate eval_map_wq\n");
+       trace_init_wq = alloc_workqueue("trace_init_wq", WQ_UNBOUND, 0);
+       if (!trace_init_wq) {
+               pr_err("Unable to allocate trace_init_wq\n");
                /* Do work here */
                eval_map_work_func(&eval_map_work);
                return -ENOMEM;
        }
 
-       queue_work(eval_map_wq, &eval_map_work);
+       queue_work(trace_init_wq, &eval_map_work);
        return 0;
 }
 
@@ -10807,8 +10807,8 @@ subsys_initcall(trace_eval_init);
 static int __init trace_eval_sync(void)
 {
        /* Make sure the eval map updates are finished */
-       if (eval_map_wq)
-               destroy_workqueue(eval_map_wq);
+       if (trace_init_wq)
+               destroy_workqueue(trace_init_wq);
        return 0;
 }
 
@@ -10969,9 +10969,9 @@ static __init int tracer_init_tracefs(void)
        if (ret)
                return 0;
 
-       if (eval_map_wq) {
+       if (trace_init_wq) {
                INIT_WORK(&tracerfs_init_work, tracer_init_tracefs_work_func);
-               queue_work(eval_map_wq, &tracerfs_init_work);
+               queue_work(trace_init_wq, &tracerfs_init_work);
        } else {
                tracer_init_tracefs_work_func(NULL);
        }
diff --git a/kernel/trace/trace.h b/kernel/trace/trace.h
index de4e6713b84e..e52f259f8945 100644
--- a/kernel/trace/trace.h
+++ b/kernel/trace/trace.h
@@ -770,6 +770,8 @@ extern unsigned long nsecs_to_usecs(unsigned long nsecs);
 
 extern unsigned long tracing_thresh;
 
+extern struct workqueue_struct *trace_init_wq __initdata;
+
 /* PID filtering */
 
 bool trace_find_filtered_pid(struct trace_pid_list *filtered_pids,
-- 
2.25.1


Reply via email to