diff options
Diffstat (limited to 'sys/ddb/ddb.h')
-rw-r--r-- | sys/ddb/ddb.h | 136 |
1 files changed, 90 insertions, 46 deletions
diff --git a/sys/ddb/ddb.h b/sys/ddb/ddb.h index 57c5fd1..1afdfa3 100644 --- a/sys/ddb/ddb.h +++ b/sys/ddb/ddb.h @@ -43,6 +43,9 @@ SYSCTL_DECL(_debug_ddb); #include <machine/db_machdep.h> /* type definitions */ +#include <sys/queue.h> /* LIST_* */ +#include <sys/kernel.h> /* SYSINIT */ + #ifndef DB_MAXARGS #define DB_MAXARGS 10 #endif @@ -73,36 +76,97 @@ SYSCTL_DECL(_debug_ddb); int DB_CALL(db_expr_t, db_expr_t *, int, db_expr_t[]); #endif +/* + * There are three "command tables": + * - One for simple commands; a list of these is displayed + * by typing 'help' at the debugger prompt. + * - One for sub-commands of 'show'; to see this type 'show' + * without any arguments. + * - The last one for sub-commands of 'show all'; type 'show all' + * without any argument to get a list. + */ +struct command; +LIST_HEAD(command_table, command); +extern struct command_table db_cmd_table; +extern struct command_table db_show_table; +extern struct command_table db_show_all_table; + +/* + * Type signature for a function implementing a ddb command. + */ typedef void db_cmdfcn_t(db_expr_t addr, boolean_t have_addr, db_expr_t count, char *modif); -#define DB_COMMAND(cmd_name, func_name) \ - DB_FUNC(cmd_name, func_name, db_cmd_set, 0, NULL) -#define DB_SHOW_COMMAND(cmd_name, func_name) \ - DB_FUNC(cmd_name, func_name, db_show_cmd_set, 0, NULL) -#define DB_SHOW_ALL_COMMAND(cmd_name, func_name) \ - DB_FUNC(cmd_name, func_name, db_show_all_cmd_set, 0, NULL) - -#define DB_SET(cmd_name, func_name, set, flag, more) \ -static const struct command __CONCAT(cmd_name,_cmd) = { \ - __STRING(cmd_name), \ - func_name, \ - flag, \ - more \ +/* + * Command table entry. + */ +struct command { + char * name; /* command name */ + db_cmdfcn_t *fcn; /* function to call */ + int flag; /* extra info: */ +#define CS_OWN 0x1 /* non-standard syntax */ +#define CS_MORE 0x2 /* standard syntax, but may have other words + * at end */ +#define CS_SET_DOT 0x100 /* set dot after command */ + struct command_table *more; /* another level of command */ + LIST_ENTRY(command) next; /* next entry in the command table */ +}; + +/* + * Arrange for the specified ddb command to be defined and + * bound to the specified function. Commands can be defined + * in modules in which case they will be available only when + * the module is loaded. + */ +#define _DB_SET(_suffix, _name, _func, list, _flag, _more) \ +static struct command __CONCAT(_name,_suffix) = { \ + .name = __STRING(_name), \ + .fcn = _func, \ + .flag = _flag, \ + .more = _more \ }; \ -TEXT_SET(set, __CONCAT(cmd_name,_cmd)) +static void __CONCAT(__CONCAT(_name,_suffix),_add)(void *arg __unused) \ + { db_command_register(&list, &__CONCAT(_name,_suffix)); } \ +SYSINIT(__CONCAT(_name,_suffix), SI_SUB_KLD, SI_ORDER_ANY, \ + __CONCAT(__CONCAT(_name,_suffix),_add), NULL); \ +static void __CONCAT(__CONCAT(_name,_suffix),_del)(void *arg __unused) \ + { db_command_unregister(&list, &__CONCAT(_name,_suffix)); } \ +SYSUNINIT(__CONCAT(_name,_suffix), SI_SUB_KLD, SI_ORDER_ANY, \ + __CONCAT(__CONCAT(_name,_suffix),_del), NULL); -#define DB_FUNC(cmd_name, func_name, set, flag, more) \ -static db_cmdfcn_t func_name; \ - \ -DB_SET(cmd_name, func_name, set, flag, more); \ - \ +/* + * Like _DB_SET but also create the function declaration which + * must be followed immediately by the body; e.g. + * _DB_FUNC(_cmd, panic, db_panic, db_cmd_table, 0, NULL) + * { + * ...panic implementation... + * } + * + * This macro is mostly used to define commands placed in one of + * the ddb command tables; see DB_COMMAND, etc. below. + */ +#define _DB_FUNC(_suffix, _name, _func, list, _flag, _more) \ +static db_cmdfcn_t _func; \ +_DB_SET(_suffix, _name, _func, list, _flag, _more); \ static void \ -func_name(addr, have_addr, count, modif) \ - db_expr_t addr; \ - boolean_t have_addr; \ - db_expr_t count; \ - char *modif; +_func(db_expr_t addr, boolean_t have_addr, db_expr_t count, char *modif) + +/* common idom provided for backwards compatibility */ +#define DB_FUNC(_name, _func, list, _flag, _more) \ + _DB_FUNC(_cmd, _name, _func, list, _flag, _more) + +#define DB_COMMAND(cmd_name, func_name) \ + _DB_FUNC(_cmd, cmd_name, func_name, db_cmd_table, 0, NULL) +#define DB_ALIAS(alias_name, func_name) \ + _DB_SET(_cmd, alias_name, func_name, db_cmd_table, 0, NULL) +#define DB_SHOW_COMMAND(cmd_name, func_name) \ + _DB_FUNC(_show, cmd_name, func_name, db_show_table, 0, NULL) +#define DB_SHOW_ALIAS(alias_name, func_name) \ + _DB_SET(_show, alias_name, func_name, db_show_table, 0, NULL) +#define DB_SHOW_ALL_COMMAND(cmd_name, func_name) \ + _DB_FUNC(_show_all, cmd_name, func_name, db_show_all_table, 0, NULL) +#define DB_SHOW_ALL_ALIAS(alias_name, func_name) \ + _DB_SET(_show_all, alias_name, func_name, db_show_all_table, 0, NULL) extern db_expr_t db_maxoff; extern int db_indent; @@ -150,6 +214,8 @@ void db_trace_self(void); int db_trace_thread(struct thread *, int); int db_value_of_name(const char *name, db_expr_t *valuep); int db_write_bytes(vm_offset_t addr, size_t size, char *data); +void db_command_register(struct command_table *, struct command *); +void db_command_unregister(struct command_table *, struct command *); db_cmdfcn_t db_breakpoint_cmd; db_cmdfcn_t db_capture_cmd; @@ -179,28 +245,6 @@ db_cmdfcn_t db_watchpoint_cmd; db_cmdfcn_t db_write_cmd; /* - * Command table. - */ -struct command; - -struct command_table { - struct command *table; - struct command **aux_tablep; - struct command **aux_tablep_end; -}; - -struct command { - char * name; /* command name */ - db_cmdfcn_t *fcn; /* function to call */ - int flag; /* extra info: */ -#define CS_OWN 0x1 /* non-standard syntax */ -#define CS_MORE 0x2 /* standard syntax, but may have other words - * at end */ -#define CS_SET_DOT 0x100 /* set dot after command */ - struct command_table *more; /* another level of command */ -}; - -/* * Interface between DDB and the DDB output capture facility. */ struct dumperinfo; |