summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/dynamic_debug.c49
1 files changed, 49 insertions, 0 deletions
diff --git a/lib/dynamic_debug.c b/lib/dynamic_debug.c
index 8675717c0f16..8fba40179305 100644
--- a/lib/dynamic_debug.c
+++ b/lib/dynamic_debug.c
@@ -862,6 +862,41 @@ int ddebug_add_module(struct _ddebug *tab, unsigned int n,
}
EXPORT_SYMBOL_GPL(ddebug_add_module);
+/* handle both dyndbg=".." and $module.dyndbg=".." params at boot */
+static int ddebug_dyndbg_boot_param_cb(char *param, char *val,
+ const char *unused)
+{
+ const char *modname = NULL;
+ char *sep;
+
+ sep = strchr(param, '.');
+ if (sep) {
+ *sep = '\0';
+ modname = param;
+ param = sep + 1;
+ }
+ if (strcmp(param, "dyndbg"))
+ return 0; /* skip all other params w/o error */
+
+ vpr_info("module: %s %s=\"%s\"\n", modname, param, val);
+
+ ddebug_exec_queries(val ? val : "+p");
+ return 0; /* query failure shouldnt stop module load */
+}
+
+/* handle dyndbg args to modprobe */
+int ddebug_dyndbg_module_param_cb(char *param, char *val, const char *doing)
+{
+ if (strcmp(param, "dyndbg"))
+ return -ENOENT;
+
+ vpr_info("module: %s %s=\"%s\"\n", doing, param, val);
+
+ ddebug_exec_queries((val ? val : "+p"));
+
+ return 0; /* query failure shouldnt stop module load */
+}
+
static void ddebug_table_free(struct ddebug_table *dt)
{
list_del_init(&dt->link);
@@ -929,6 +964,7 @@ static int __init dynamic_debug_init(void)
{
struct _ddebug *iter, *iter_start;
const char *modname = NULL;
+ char *cmdline;
int ret = 0;
int n = 0;
@@ -967,6 +1003,18 @@ static int __init dynamic_debug_init(void)
/* keep tables even on ddebug_query parse error */
ret = 0;
}
+ /* now that ddebug tables are loaded, process all boot args
+ * again to find and activate queries given in dyndbg params.
+ * While this has already been done for known boot params, it
+ * ignored the unknown ones (dyndbg in particular). Reusing
+ * parse_args avoids ad-hoc parsing. This will also attempt
+ * to activate queries for not-yet-loaded modules, which is
+ * slightly noisy if verbose, but harmless.
+ */
+ cmdline = kstrdup(saved_command_line, GFP_KERNEL);
+ parse_args("dyndbg params", cmdline, NULL,
+ 0, 0, 0, &ddebug_dyndbg_boot_param_cb);
+ kfree(cmdline);
out_free:
if (ret)
@@ -977,5 +1025,6 @@ out_free:
}
/* Allow early initialization for boot messages via boot param */
arch_initcall(dynamic_debug_init);
+
/* Debugfs setup must be done later */
module_init(dynamic_debug_init_debugfs);