Allow dynamic enabling/disabling of kstackwatch through user input of proc. With this patch, the entire system becomes functional. Signed-off-by: Jinchao Wang --- mm/kstackwatch/kernel.c | 55 ++++++++++++++++++++++++++++++++++++++++- 1 file changed, 54 insertions(+), 1 deletion(-) diff --git a/mm/kstackwatch/kernel.c b/mm/kstackwatch/kernel.c index 8e1dca45003e..9ef969f28e29 100644 --- a/mm/kstackwatch/kernel.c +++ b/mm/kstackwatch/kernel.c @@ -17,6 +17,43 @@ MODULE_LICENSE("GPL"); static struct ksw_config *ksw_config; static atomic_t config_file_busy = ATOMIC_INIT(0); +static bool watching_active; + +static int ksw_start_watching(void) +{ + int ret; + + /* + * Watch init will preallocate the HWBP, + * so it must happen before stack init + */ + ret = ksw_watch_init(); + if (ret) { + pr_err("ksw_watch_init ret: %d\n", ret); + return ret; + } + + ret = ksw_stack_init(); + if (ret) { + pr_err("ksw_stack_init ret: %d\n", ret); + ksw_watch_exit(); + return ret; + } + watching_active = true; + + pr_info("start watching: %s\n", ksw_config->config_str); + return 0; +} + +static void ksw_stop_watching(void) +{ + ksw_stack_exit(); + ksw_watch_exit(); + watching_active = false; + + pr_info("stop watching: %s\n", ksw_config->config_str); +} + /* * Format of the configuration string: * function+ip_offset[+depth] [local_var_offset:local_var_len] @@ -109,6 +146,9 @@ static ssize_t kstackwatch_proc_write(struct file *file, if (copy_from_user(input, buffer, count)) return -EFAULT; + if (watching_active) + ksw_stop_watching(); + input[count] = '\0'; strim(input); @@ -123,12 +163,22 @@ static ssize_t kstackwatch_proc_write(struct file *file, return ret; } + ret = ksw_start_watching(); + if (ret) { + pr_err("Failed to start watching with %d\n", ret); + return ret; + } + return count; } static int kstackwatch_proc_show(struct seq_file *m, void *v) { - seq_printf(m, "%s\n", ksw_config->config_str); + if (watching_active) + seq_printf(m, "%s\n", ksw_config->config_str); + else + seq_puts(m, "not watching\n"); + return 0; } @@ -176,6 +226,9 @@ static int __init kstackwatch_init(void) static void __exit kstackwatch_exit(void) { + if (watching_active) + ksw_stop_watching(); + remove_proc_entry("kstackwatch", NULL); kfree(ksw_config); -- 2.43.0