Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/netbsd-1-6]: src/dist/bind/bin/ndc Pull up revisions 1.6-1.7 (requested ...



details:   https://anonhg.NetBSD.org/src/rev/e7c2a91e6c3c
branches:  netbsd-1-6
changeset: 528155:e7c2a91e6c3c
user:      lukem <lukem%NetBSD.org@localhost>
date:      Fri Jun 28 11:35:53 2002 +0000

description:
Pull up revisions 1.6-1.7 (requested by itojun in ticket #387):
Update to BIND 8.3.3.  Fixes buffer overrun in resolver code.

diffstat:

 dist/bind/bin/ndc/ndc.c |  240 +++++++++++++++++++++++++++++++++++++++++------
 1 files changed, 207 insertions(+), 33 deletions(-)

diffs (truncated from 365 to 300 lines):

diff -r cedcfe6a02f5 -r e7c2a91e6c3c dist/bind/bin/ndc/ndc.c
--- a/dist/bind/bin/ndc/ndc.c   Fri Jun 28 11:35:44 2002 +0000
+++ b/dist/bind/bin/ndc/ndc.c   Fri Jun 28 11:35:53 2002 +0000
@@ -1,7 +1,7 @@
-/*     $NetBSD: ndc.c,v 1.5 2001/09/24 13:22:27 wiz Exp $      */
+/*     $NetBSD: ndc.c,v 1.5.2.1 2002/06/28 11:35:53 lukem Exp $        */
 
 #if !defined(lint) && !defined(SABER)
-static const char rcsid[] = "Id: ndc.c,v 1.16.2.1 2001/04/26 02:56:10 marka Exp";
+static const char rcsid[] = "Id: ndc.c,v 1.22 2002/06/24 07:28:55 marka Exp";
 #endif /* not lint */
 
 /*
@@ -62,7 +62,7 @@
 
 static const char *    program = "amnesia";
 static enum { e_channel, e_signals } mode = e_channel;
-static char *  channel = _PATH_NDCSOCK;
+static const char *    channel = _PATH_NDCSOCK;
 static const char      helpfmt[] = "\t%-16s\t%s\n";
 static const char *    pidfile = _PATH_PIDFILE;
 static sockaddr_t      client, server;
@@ -79,32 +79,23 @@
 static void            command(void);
 static int             running(int, pid_t *);
 static void            command_channel(void);
-static void            channel_loop(char *, int, closure, void *);
+static void            channel_loop(const char *, int, closure, void *);
 static void            getpid_closure(void *, const char *, int);
 static void            banner(struct ctl_cctx *, void *, const char *, u_int);
 static void            done(struct ctl_cctx *, void *, const char *, u_int);
-static void            logger(enum ctl_severity, const char *fmt, ...)
-     __attribute__((__format__(__printf__, 2, 3)));
+static void            logger(enum ctl_severity, const char *fmt, ...) ISC_FORMAT_PRINTF(2, 3);
 static void            command_signals(void);
 static void            stop_named(pid_t);
 static void            start_named(const char *, int);
 static int             fgetpid(const char *, pid_t *);
-static int             get_sockaddr(char *, sockaddr_t *);
+static int             get_sockaddr(const char *, sockaddr_t *);
 static size_t          impute_addrlen(const struct sockaddr *);
-static void            vtrace(const char *, va_list)
-     __attribute__((__format__(__printf__, 1, 0)));
-static void            trace(const char *, ...)
-     __attribute__((__format__(__printf__, 1, 2)));
-static void            result(const char *, ...)
-     __attribute__((__format__(__printf__, 1, 2)));
-static void            fatal(const char *, ...)
-     __attribute__((__format__(__printf__, 1, 2)));
-static void            verror(const char *, va_list)
-     __attribute__((__format__(__printf__, 1, 0)));
-static void            error(const char *, ...)
-     __attribute__((__format__(__printf__, 1, 2)));
-static void usage(const char *fmt, ...)
-     __attribute__((__format__(__printf__, 1, 2)));
+static void            vtrace(const char *, va_list) ISC_FORMAT_PRINTF(1, 0);
+static void            trace(const char *, ...) ISC_FORMAT_PRINTF(1, 2);
+static void            result(const char *, ...) ISC_FORMAT_PRINTF(1, 2);
+static void            fatal(const char *, ...) ISC_FORMAT_PRINTF(1, 2);
+static void            verror(const char *, va_list) ISC_FORMAT_PRINTF(1, 0);
+static void            error(const char *, ...) ISC_FORMAT_PRINTF(1, 2);
 
 static void
 usage(const char *fmt, ...) {
@@ -125,7 +116,7 @@
 /* Public. */
 
 int
-main(int argc, char *argv[], char *envp[]) {
+main(int argc, char *argv[]) {
        char *p;
        int ch;
 
@@ -261,6 +252,179 @@
               "toggle silence (suppresses nonfatal errors)");
 }
 
+struct argv {
+       int argc;
+       char **argv;
+       int error;
+};
+
+static char hexdigits[] = "0123456789abcdef";
+
+static void
+getargs_closure(void *arg, const char *msg, int flags) {
+       struct argv *argv = arg;
+       int len;
+       int i;
+       const char *cp, *cp2;
+       char *tp, c;
+
+       UNUSED(flags);
+
+       if (argv->error)
+               return;
+
+       if (argv->argc == -1) {
+               i = atoi(msg + 4);
+               if (i < 1) {
+                       argv->error = 1;
+                       return;
+               }
+               argv->argc = i;
+               argv->argv = calloc((i+1), sizeof(char*));
+               return;
+       }
+       len = 0;
+       cp = msg + 4;
+       while (*cp != NULL) {
+               c = *cp;
+               if (c == '%') {
+                       cp2 = strchr(hexdigits, cp[1]);
+                       if (cp2 == NULL) {
+                               argv->error = 1;
+                               return;
+                       }
+                       c = (cp2-hexdigits) << 4;
+                       cp2 = strchr(hexdigits, cp[2]);
+                       if (cp2 == NULL) {
+                               argv->error = 1;
+                               return;
+                       }
+                       c += (cp2-hexdigits);
+                       cp += 2;
+               }
+               if (!isalnum((unsigned)c)) {
+                       switch (c) {
+                       case '+': case '-': case '=': case '/': case '.':
+                               break;
+                       default:
+                               len++;
+                       }
+               }
+               len++;
+               cp++;
+       }
+       i = 0;
+       while (argv->argv[i] != NULL)
+               i++;
+       if (i >= argv->argc) {
+               argv->error = 1;
+               return;
+       }
+       argv->argv[i] = malloc(len + 1);
+       if (argv->argv[i] == NULL) {
+               argv->error = 1;
+               return;
+       }
+       cp = msg + 4;
+       tp = argv->argv[i];
+       while (*cp != NULL) {
+               c = *cp;
+               if (c == '%') {
+                       cp2 = strchr(hexdigits, cp[1]);
+                       if (cp2 == NULL) {
+                               argv->error = 1;
+                               return;
+                       }
+                       c = (cp2-hexdigits) << 4;
+                       cp2 = strchr(hexdigits, cp[2]);
+                       if (cp2 == NULL) {
+                               argv->error = 1;
+                               return;
+                       }
+                       c += (cp2-hexdigits);
+                       cp += 2;
+               }
+               if (!isalnum((unsigned)c)) {
+                       switch (c) {
+                       case '+': case '-': case '=': case '/': case '.':
+                               break;
+                       default:
+                               *tp = '\\';
+                       }
+               }
+               *tp++ = c;
+               cp++;
+       }
+}
+
+static int
+get_args(char **restp) {
+       struct argv argv;
+       int len, i;
+       char *rest, *p;
+       int result = 1;
+
+       argv.argc = -1;
+       argv.argv = NULL;
+       argv.error = 0;
+
+       channel_loop("args", 1, getargs_closure, &argv);
+       if (argv.error) {
+               result = 0;
+               goto err;
+       }
+       len = 0;
+       for (i = 1 ; i < argv.argc && argv.argv[i] != NULL; i++)
+               len += strlen(argv.argv[i]) + 1;
+       rest = malloc(len);
+       if (rest == NULL) {
+               result = 0;
+               goto err;
+       }
+       p = rest;
+       for (i = 1 ; i < argv.argc && argv.argv[i] != NULL; i++) {
+               strcpy(p, argv.argv[i]);
+               p += strlen(argv.argv[i]);
+               *p++ = ' ';
+       }
+       if (p != rest)
+               p[-1] = '\0';
+       *restp = rest;
+
+ err:
+       if (argv.argv) {
+               for (i = 0 ; i < argv.argc && argv.argv[i] != NULL; i++)
+                       free(argv.argv[i]);
+               free(argv.argv);
+       }
+       return (result);
+}
+
+static void
+exec_closure(void *arg, const char *msg, int flags) {
+       int *result = arg;
+       UNUSED(flags);
+       if (atoi(msg) == 250)
+               *result = 1;
+}
+
+static int
+try_exec(int local_quiet) {
+       int good = 0;
+       pid_t pid;
+
+       channel_loop("exec", 1, exec_closure, &good);
+
+       if (good) {
+               sleep(3);
+               if (!running(0, &pid))
+                       error("name server has not restarted (yet?)");
+               else if (!local_quiet)
+                       result("new pid is %ld", (long)pid);
+       }
+       return (good);
+}
+
 static int
 builtincmd(void) {
        static const char spaces[] = " \t";
@@ -268,14 +432,18 @@
        pid_t pid;
        int save_quiet = quiet;
        int len;
+       int freerest = 0;
 
        quiet = 1;
 
        len = strcspn(cmd, spaces);
        rest = cmd + len;
-       if (*rest != '\0') {
-               rest++;
+       if (*rest != '\0')
                rest += strspn(rest, spaces);
+       if (*rest == '\0' && !strncasecmp(cmd, "restart", len)) {
+               if (try_exec(save_quiet))
+                       return (1);
+               freerest = get_args(&rest);
        }
        syscmd = malloc(strlen(named_path) + sizeof " " + strlen(rest));
        if (syscmd == NULL)
@@ -285,6 +453,8 @@
                strcat(syscmd, " ");
                strcat(syscmd, rest);
        }
+       if (freerest)
+               free(rest);
        if (strncasecmp(cmd, "start", len) == 0) {
                if (running(debug, &pid))
                        error("name server already running? (pid %ld)",
@@ -413,7 +583,7 @@
 };
 
 static void
-channel_loop(char *cmdtext, int show, closure cl, void *ua) {
+channel_loop(const char *cmdtext, int show, closure cl, void *ua) {
        struct ctl_cctx *ctl;
        struct sockaddr *client_addr;
        struct args a;
@@ -428,6 +598,7 @@
        a.cl = cl;
        a.ua = ua;
        logger_show = show;
+       trace("command '%s'", cmdtext);
        ctl = ctl_client(ev, client_addr, impute_addrlen(client_addr),
                         (struct sockaddr *)&server,
                         impute_addrlen((struct sockaddr *)&server),



Home | Main Index | Thread Index | Old Index