Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 18 Aug 2008 10:02:14 -0400
From:      John Baldwin <jhb@freebsd.org>
To:        freebsd-hackers@freebsd.org
Cc:        Guillaume Ballet <gballet@gmail.com>, Sam Leffler <sam@freebsd.org>
Subject:   Re: Extending the ddb command set
Message-ID:  <200808181002.14885.jhb@freebsd.org>
In-Reply-To: <fd183dc60808171017m7eabcef2xbe1845e54cda4c99@mail.gmail.com>
References:  <fd183dc60808160203r3d90c26dq4d282d2ef153d2db@mail.gmail.com> <48A70B37.60401@freebsd.org> <fd183dc60808171017m7eabcef2xbe1845e54cda4c99@mail.gmail.com>

next in thread | previous in thread | raw e-mail | index | archive | help
On Sunday 17 August 2008 01:17:54 pm Guillaume Ballet wrote:
> On Sat, Aug 16, 2008 at 5:15 PM, Sam Leffler <sam@freebsd.org> wrote:
> > Guillaume Ballet wrote:
> >> Hello hackers,
> >>
> >> I am currently working on a small project and would like to add a few
> >> commands to the set that is available in ddb.
> >>
> >> I found that very interesting albeit succinct presentation:
> >> http://people.freebsd.org/~jhb/papers/bsdcan/2008/slides.odp<http://peop
> >>le.freebsd.org/%7Ejhb/papers/bsdcan/2008/slides.odp>
> >>
> >> where the author hints that I should use DB_COMMAND, which I did. Yet
> >> when invoking ddb, the command does not appear in the help list. I have
> >> taken a look at the source code and was expecting set_db_cmd_set to
> >> appear in my module's section list when calling objdump -h
> >>
> >> Is DB_COMMAND only working within the kernel itself, and not modules?
> >
> > That is correct; you can't add ddb cmds from modules.  It should be
> > doable; just hasn't been done yet.
> >
> >   Sam
>
> It is indeed doable: Here are the diffs for a first attempt at doing
> this. I am not entirely satisfied with it, though, as it does not work
> with DB_SHOW_COMMAND and the likes... Also, I have to declare a lot of
> ddb-related stuff into kern_linker.c and I don't like it. I am
> currently working at improving the whole thing, but in the mean time
> if someone wants to give it a try, comments/rants would be greatly
> appreciated.

A simpler approach is probably to make DB_COMMAND() use a SYSINIT to register 
new functions instead of teaching DDB about that linker set.  You just need 
to write a shared "register_command()" function (and a deregister for 
SYSUNINIT for module unload) that the SYSINIT uses.  This also probably 
requires changing the structure of the DDB tables, though you might be able 
to make it simpler now.  You could probably just make the tables be sorted 
linked lists now instead of arrays.  This would also remove the whole "aux 
table" hack.

> Guillaume
>
> --- sys/linker.h.orig    2008-08-17 18:45:56.000000000 +0200
> +++ sys/linker.h    2008-08-17 18:50:57.000000000 +0200
> @@ -155,6 +155,9 @@
>  int linker_ddb_search_symbol(caddr_t _value, c_linker_sym_t *_sym,
>                   long *_diffp);
>  int linker_ddb_symbol_values(c_linker_sym_t _sym, linker_symval_t
> *_symval); +struct command;
> +int linker_ddb_cmd_search(char *, struct command **);
> +int linker_ddb_cmd_list(void);
>
>
>  /* HWPMC helper */
> --- kern/kern_linker.c.orig    2008-08-17 08:38:51.000000000 +0200
> +++ kern/kern_linker.c    2008-08-17 18:47:45.000000000 +0200
> @@ -777,6 +777,9 @@
>   * that the files list is inconsistant instead.
>   */
>
> +#include <ddb/ddb.h>
> +#include <ddb/db_output.h>
> +
>  int
>  linker_ddb_lookup(const char *symstr, c_linker_sym_t *sym)
>  {
> @@ -831,6 +834,52 @@
>      }
>      return (ENOENT);
>  }
> +
> +int linker_ddb_cmd_list()
> +{
> +    linker_file_t    lf;
> +    struct command    **start, **stop, **search;
> +
> +    TAILQ_FOREACH(lf, &linker_files, link) {
> +        if (!linker_file_lookup_set(lf,"db_cmd_set",&start,&stop,NULL)) {
> +            for (search=start; search < stop; search++) {
> +                db_printf("%-12s", (*search)->name);
> +                db_end_line(12);
> +            }
> +        }
> +    }
> +
> +    return 0;
> +}
> +
> +int linker_ddb_cmd_search(char *name, struct command **cmdp)
> +{
> +    linker_file_t lf;
> +    char *lp, *rp;
> +    struct command **cmd, **start, **stop;
> +    int c;
> +
> +    TAILQ_FOREACH(lf, &linker_files, link) {
> +        if (!linker_file_lookup_set(lf, "db_cmd_set", &start, &stop,
> NULL)) { +            for (cmd=start; cmd < stop; cmd++) {
> +                lp    = name;
> +                rp    = (*cmd)->name;
> +
> +                while((c = *lp) == *rp) {
> +                    if (c == 0) {
> +                        *cmdp = *cmd;
> +                        return 0;
> +                    }
> +
> +                    lp++;
> +                    rp++;
> +                }
> +            }
> +        }
> +    }
> +
> +    return -1;
> +}
>  #endif
>
>  /*
> --- ddb/db_command.c.orig    2008-08-17 10:26:26.000000000 +0200
> +++ ddb/db_command.c    2008-08-17 18:42:22.000000000 +0200
> @@ -253,6 +253,9 @@
>              if (result == CMD_UNIQUE)
>                  return (CMD_UNIQUE);
>          }
> +    if (result == CMD_NONE && linker_ddb_cmd_search(name,cmdp) == 0) {
> +        result = CMD_UNIQUE;
> +    }
>      if (result == CMD_NONE) {
>          /* check for 'help' */
>          if (name[0] == 'h' && name[1] == 'e'
> @@ -280,6 +283,7 @@
>          db_printf("%-12s", (*aux_cmdp)->name);
>          db_end_line(12);
>      }
> +    linker_ddb_cmd_list();
>  }
>
>  static void
> --- ddb/db_command.h.orig    2008-08-17 18:37:34.000000000 +0200
> +++ ddb/db_command.h    2008-08-17 18:49:29.000000000 +0200
> @@ -46,4 +46,7 @@
>  extern db_addr_t    db_next;    /* next address to be examined
>                         or written */
>
> +extern int linker_ddb_cmd_search(char*,struct command **);
> +extern int linker_ddb_cmd_list(void);
> +
>  #endif /* !_DDB_DB_COMMAND_H_ */
> _______________________________________________
> freebsd-hackers@freebsd.org mailing list
> http://lists.freebsd.org/mailman/listinfo/freebsd-hackers
> To unsubscribe, send any mail to "freebsd-hackers-unsubscribe@freebsd.org"



-- 
John Baldwin



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200808181002.14885.jhb>