Upgrade single classes-map to list of them:

This allows multiple DYNAMIC_DEBUG_CLASSES(class-map)s per module,
using _base to segment the 0..30 classid space.

alter struct ddebug table:
 replace .classes (a &map) with maps (list-head)

dynamic_debug_register_classes(map) - adds new map to maps list.

dynamic_debug_unregister_classes(map) - deletes map after ID-check.

ddebug_validate_classname() - check all maps in list before failing.

ddebug_class_name() - which supports ```cat control``` now walks maps
list, finds the map whose sub-range of .class_id's spans the one in
the callsite, and returns that class-name.

Signed-off-by: Jim Cromie <jim.cro...@gmail.com>
---
. split out validate_classnames()
. fold in fixes for multi class-maps
---
 lib/dynamic_debug.c | 76 +++++++++++++++++++++++++++++++--------------
 1 file changed, 52 insertions(+), 24 deletions(-)

diff --git a/lib/dynamic_debug.c b/lib/dynamic_debug.c
index 8e1b9159e881..f9c5bbf9d43b 100644
--- a/lib/dynamic_debug.c
+++ b/lib/dynamic_debug.c
@@ -43,10 +43,8 @@ extern struct _ddebug __start___dyndbg[];
 extern struct _ddebug __stop___dyndbg[];
 
 struct ddebug_table {
-       struct list_head link;
+       struct list_head link, maps;
        const char *mod_name;
-       /* a module can have multiple class-sets eventually, but not yet */
-       struct ddebug_known_classes_map const *map;
        unsigned int num_ddebugs;
        struct _ddebug *ddebugs;
 };
@@ -149,28 +147,18 @@ static void vpr_info_dq(const struct ddebug_query *query, 
const char *msg)
 /* return <0 if class-name is unknown/invalid, 0..CLASS_DFLT otherwise */
 static int ddebug_validate_classname(struct ddebug_table *dt, const char 
*class_string)
 {
-       int query_class = -ENOENT;
+       struct ddebug_known_classes_map *map;
        int idx;
 
        if (!class_string)
-               /* all queries w/o class given work only on default class */
                return _DPRINTK_CLASS_DFLT;
 
-       /*
-        * XXX single list will need to be a for-list
-        * so that modules can have 2 sets of class-decls
-        */
-       if (!dt->map)
-               return -ENOENT;
-
-       idx = match_string(dt->map->classes, dt->map->length, class_string);
-       if (idx < 0) {
-               v3pr_info("class: %s.%s unknown\n", dt->mod_name, class_string);
-               return -ENOENT;
+       list_for_each_entry(map, &dt->maps, link) {
+               idx = match_string(map->classes, map->length, class_string);
+               if (idx >= 0)
+                       return idx + map->base;
        }
-       query_class = idx + dt->map->base;
-
-       return query_class;
+       return -ENOENT;
 }
 
 /*
@@ -1032,8 +1020,14 @@ static void *ddebug_proc_next(struct seq_file *m, void 
*p, loff_t *pos)
 
 static const char *ddebug_class_name(struct ddebug_iter *iter, struct _ddebug 
*dp)
 {
-       if (iter->table->map)
-               return iter->table->map->classes[dp->class_id];
+       struct ddebug_known_classes_map *map;
+
+       list_for_each_entry(map, &iter->table->maps, link) {
+               if (dp->class_id < map->base ||
+                   dp->class_id >= map->base + map->length)
+                       continue;
+               return map->classes[dp->class_id - map->base];
+       }
        return NULL;
 }
 
@@ -1124,6 +1118,7 @@ int dynamic_debug_register_classes(struct 
ddebug_known_classes_map *map)
        struct ddebug_table *dt;
        int rc = -ENOENT;
 
+       INIT_LIST_HEAD(&map->link);
        mutex_lock(&ddebug_lock);
 #ifdef CONFIG_MODULES
        if (map->mod) {
@@ -1131,7 +1126,7 @@ int dynamic_debug_register_classes(struct 
ddebug_known_classes_map *map)
                list_for_each_entry(dt, &ddebug_tables, link) {
                        if (dt->mod_name == map->mod->name) {
                                rc = 0;
-                               dt->map = map;
+                               list_add(&map->link, &dt->maps);
                                break;
                        }
                }
@@ -1142,7 +1137,7 @@ int dynamic_debug_register_classes(struct 
ddebug_known_classes_map *map)
                list_for_each_entry(dt, &ddebug_tables, link) {
                        if (!strcmp(dt->mod_name, map->mod_name)) {
                                rc = 0;
-                               dt->map = map;
+                               list_add(&map->link, &dt->maps);
                                break;
                        }
                }
@@ -1159,8 +1154,38 @@ EXPORT_SYMBOL(dynamic_debug_register_classes);
 
 void dynamic_debug_unregister_classes(struct ddebug_known_classes_map *map)
 {
-       vpr_info("unregister_classes: %s\n", map->mod_name);
+       int rc = -ENOENT;
+
+       mutex_lock(&ddebug_lock);
+#ifdef CONFIG_MODULES
+       if (map->mod) {
+               struct ddebug_known_classes_map *dmap;
+               struct ddebug_table *dt;
+
+               list_for_each_entry(dt, &ddebug_tables, link) {
+                       if (dt->mod_name != map->mod->name)
+                               continue;
+                       list_for_each_entry(dmap, &dt->maps, link) {
+                               if (dmap != map)
+                                       continue;
+                               rc = 0;
+                               list_del(&map->link);
+                               break;
+                       }
+               }
+       }
+#endif
+       if (!map->mod) {
+               pr_err("shouldn't be unloading a builtin module: %s\n",
+                      map->mod_name);
+       }
+       mutex_unlock(&ddebug_lock);
+       if (rc)
+               pr_warn("unregister_classes: module %s not found\n", 
map->mod_name);
+       else
+               vpr_info("unregister_classes: %s\n", map->mod_name);
 }
+EXPORT_SYMBOL(dynamic_debug_unregister_classes);
 
 /*
  * Allocate a new ddebug_table for the given module
@@ -1186,6 +1211,9 @@ int ddebug_add_module(struct _ddebug *tab, unsigned int n,
        dt->num_ddebugs = n;
        dt->ddebugs = tab;
 
+       INIT_LIST_HEAD(&dt->link);
+       INIT_LIST_HEAD(&dt->maps);
+
        mutex_lock(&ddebug_lock);
        list_add(&dt->link, &ddebug_tables);
        mutex_unlock(&ddebug_lock);
-- 
2.35.3

Reply via email to