Source-Changes-HG archive

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

[src/trunk]: src/usr.bin/tftp IPv6 support.



details:   https://anonhg.NetBSD.org/src/rev/c230ed922b9b
branches:  trunk
changeset: 474618:c230ed922b9b
user:      itojun <itojun%NetBSD.org@localhost>
date:      Mon Jul 12 20:19:20 1999 +0000

description:
IPv6 support.
clarify a bit (specifically, routines in tftp.c now does not
modify "peeraddr")

diffstat:

 usr.bin/tftp/Makefile   |    5 +-
 usr.bin/tftp/main.c     |  162 ++++++++++++++++++++++++++---------------------
 usr.bin/tftp/tftp.1     |    3 +-
 usr.bin/tftp/tftp.c     |   64 +++++++++++++-----
 usr.bin/tftp/tftpsubs.c |    6 +-
 5 files changed, 143 insertions(+), 97 deletions(-)

diffs (truncated from 533 to 300 lines):

diff -r c5bbcebd01ef -r c230ed922b9b usr.bin/tftp/Makefile
--- a/usr.bin/tftp/Makefile     Mon Jul 12 20:17:09 1999 +0000
+++ b/usr.bin/tftp/Makefile     Mon Jul 12 20:19:20 1999 +0000
@@ -1,7 +1,10 @@
-#      $NetBSD: Makefile,v 1.5 1997/10/20 00:45:33 lukem Exp $
+#      $NetBSD: Makefile,v 1.6 1999/07/12 20:19:20 itojun Exp $
 #      @(#)Makefile    8.1 (Berkeley) 6/6/93
 
 PROG=  tftp
 SRCS=  main.c tftp.c tftpsubs.c
 
+# cope with past spec changes
+CPPFLAGS+=-Dss_len=__ss_len -Dss_family=__ss_family
+
 .include <bsd.prog.mk>
diff -r c5bbcebd01ef -r c230ed922b9b usr.bin/tftp/main.c
--- a/usr.bin/tftp/main.c       Mon Jul 12 20:17:09 1999 +0000
+++ b/usr.bin/tftp/main.c       Mon Jul 12 20:19:20 1999 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: main.c,v 1.10 1998/12/19 22:41:21 christos Exp $       */
+/*     $NetBSD: main.c,v 1.11 1999/07/12 20:19:20 itojun Exp $ */
 
 /*
  * Copyright (c) 1983, 1993
@@ -40,7 +40,7 @@
 #if 0
 static char sccsid[] = "@(#)main.c     8.1 (Berkeley) 6/6/93";
 #else
-__RCSID("$NetBSD: main.c,v 1.10 1998/12/19 22:41:21 christos Exp $");
+__RCSID("$NetBSD: main.c,v 1.11 1999/07/12 20:19:20 itojun Exp $");
 #endif
 #endif /* not lint */
 
@@ -73,9 +73,8 @@
 #define        TIMEOUT         5               /* secs between rexmt's */
 #define        LBUFLEN         200             /* size of input buffer */
 
-struct sockaddr_in peeraddr;
+struct sockaddr_storage peeraddr;
 int    f;
-short   port;
 int    trace;
 int    verbose;
 int    connected;
@@ -85,7 +84,6 @@
 char   *margv[20];
 char   *prompt = "tftp";
 jmp_buf        toplevel;
-struct servent *sp;
 
 void   get __P((int, char **));
 void   help __P((int, char **));
@@ -94,6 +92,7 @@
 void   quit __P((int, char **));
 void   setascii __P((int, char **));
 void   setbinary __P((int, char **));
+void   setpeer0 __P((char *, char *));
 void   setpeer __P((int, char **));
 void   setrexmt __P((int, char **));
 void   settimeout __P((int, char **));
@@ -156,18 +155,7 @@
        int argc;
        char *argv[];
 {
-       struct sockaddr_in s_in;
-
-       sp = getservbyname("tftp", "udp");
-       if (sp == 0)
-               errx(1, "udp/tftp: unknown service");
-       f = socket(AF_INET, SOCK_DGRAM, 0);
-       if (f < 0)
-               err(3, "socket");
-       memset((char *)&s_in, 0, sizeof (s_in));
-       s_in.sin_family = AF_INET;
-       if (bind(f, (struct sockaddr *)&s_in, sizeof (s_in)) < 0)
-               err(1, "bind");
+       f = -1;
        strcpy(mode, "netascii");
        signal(SIGINT, intr);
        if (argc > 1) {
@@ -184,11 +172,73 @@
 char    hostname[100];
 
 void
+setpeer0(host, port)
+       char *host;
+       char *port;
+{
+       struct addrinfo hints, *res0, *res;
+       int error;
+       struct sockaddr_storage ss;
+       char *cause = "unknown";
+
+       if (connected) {
+               close(f);
+               f = -1;
+               connected = 0;
+       }
+
+       memset(&hints, 0, sizeof(hints));
+       hints.ai_family = PF_UNSPEC;
+       hints.ai_socktype = SOCK_DGRAM;
+       hints.ai_protocol = IPPROTO_UDP;
+       hints.ai_flags = AI_CANONNAME;
+       if (!port)
+               port = "tftp";
+       error = getaddrinfo(host, port, &hints, &res0);
+       if (error) {
+               warnx("%s", gai_strerror(error));
+               return;
+       }
+
+       for (res = res0; res; res = res->ai_next) {
+               f = socket(res->ai_family, res->ai_socktype, res->ai_protocol);
+               if (f < 0) {
+                       cause = "socket";
+                       continue;
+               }
+
+               memset(&ss, 0, sizeof(ss));
+               ss.ss_family = res->ai_family;
+               ss.ss_len = res->ai_addrlen;
+               if (bind(f, (struct sockaddr *)&ss, ss.ss_len) < 0) {
+                       cause = "bind";
+                       close(f);
+                       f = -1;
+                       continue;
+               }
+
+               break;
+       }
+
+       if (f < 0)
+               warn("%s", cause);
+       else {
+               memcpy(&peeraddr, res->ai_addr, res->ai_addrlen);
+               if (res->ai_canonname) {
+                       (void) strncpy(hostname, res->ai_canonname,
+                               sizeof(hostname));
+               } else
+                       (void) strncpy(hostname, host, sizeof(hostname));
+               hostname[sizeof(hostname)-1] = 0;
+               connected = 1;
+       }
+}
+
+void
 setpeer(argc, argv)
        int argc;
        char *argv[];
 {
-       struct hostent *host;
 
        if (argc < 2) {
                strcpy(line, "Connect ");
@@ -202,32 +252,10 @@
                printf("usage: %s host-name [port]\n", argv[0]);
                return;
        }
-       if (inet_aton(argv[1], &peeraddr.sin_addr) != 0) {
-               peeraddr.sin_family = AF_INET;
-               (void) strcpy(hostname, argv[1]);
-       } else {
-               host = gethostbyname(argv[1]);
-               if (host == 0) {
-                       connected = 0;
-                       printf("%s: unknown host\n", argv[1]);
-                       return;
-               }
-               peeraddr.sin_family = host->h_addrtype;
-               memmove(&peeraddr.sin_addr, host->h_addr, host->h_length);
-               (void) strncpy(hostname, host->h_name, sizeof(hostname));
-               hostname[sizeof(hostname)-1] = 0;
-       }
-       port = sp->s_port;
-       if (argc == 3) {
-               port = atoi(argv[2]);
-               if (port < 0) {
-                       printf("%s: bad port number\n", argv[2]);
-                       connected = 0;
-                       return;
-               }
-               port = htons(port);
-       }
-       connected = 1;
+       if (argc == 3)
+               setpeer0(argv[1], NULL);
+       else
+               setpeer0(argv[1], argv[2]);
 }
 
 struct modes {
@@ -331,9 +359,8 @@
                return;
        }
        targ = argv[argc - 1];
-       if (strchr(argv[argc - 1], ':')) {
+       if (strrchr(argv[argc - 1], ':')) {
                char *cp;
-               struct hostent *hp;
 
                for (n = 1; n < argc - 1; n++)
                        if (strchr(argv[n], ':')) {
@@ -341,18 +368,13 @@
                                return;
                        }
                cp = argv[argc - 1];
-               targ = strchr(cp, ':');
+               targ = strrchr(cp, ':');
                *targ++ = 0;
-               hp = gethostbyname(cp);
-               if (hp == NULL) {
-                       warnx("%s: %s", cp, hstrerror(h_errno));
-                       return;
+               if (cp[0] == '[' && cp[strlen(cp) - 1] == ']') {
+                       cp[strlen(cp) - 1] = '\0';
+                       cp++;
                }
-               memmove((caddr_t)&peeraddr.sin_addr, hp->h_addr, hp->h_length);
-               peeraddr.sin_family = hp->h_addrtype;
-               connected = 1;
-               strncpy(hostname, hp->h_name, sizeof(hostname));
-               hostname[sizeof(hostname)-1] = 0;
+               setpeer0(cp, NULL);
        }
        if (!connected) {
                printf("No target machine specified.\n");
@@ -368,7 +390,6 @@
                if (verbose)
                        printf("putting %s to %s:%s [%s]\n",
                                cp, hostname, targ, mode);
-               peeraddr.sin_port = port;
                sendfile(fd, targ, mode);
                return;
        }
@@ -386,7 +407,6 @@
                if (verbose)
                        printf("putting %s to %s:%s [%s]\n",
                                argv[n], hostname, targ, mode);
-               peeraddr.sin_port = port;
                sendfile(fd, targ, mode);
        }
 }
@@ -426,30 +446,26 @@
        }
        if (!connected) {
                for (n = 1; n < argc ; n++)
-                       if (strchr(argv[n], ':') == 0) {
+                       if (strrchr(argv[n], ':') == 0) {
                                getusage(argv[0]);
                                return;
                        }
        }
        for (n = 1; n < argc ; n++) {
-               src = strchr(argv[n], ':');
+               src = strrchr(argv[n], ':');
                if (src == NULL)
                        src = argv[n];
                else {
-                       struct hostent *hp;
-
+                       char *cp;
                        *src++ = 0;
-                       hp = gethostbyname(argv[n]);
-                       if (hp == NULL) {
-                               warnx("%s: %s", argv[n], hstrerror(h_errno));
+                       cp = argv[n];
+                       if (cp[0] == '[' && cp[strlen(cp) - 1] == ']') {
+                               cp[strlen(cp) - 1] = '\0';
+                               cp++;
+                       }
+                       setpeer0(cp, NULL);
+                       if (!connected)
                                continue;
-                       }
-                       memmove((caddr_t)&peeraddr.sin_addr, hp->h_addr,
-                           hp->h_length);
-                       peeraddr.sin_family = hp->h_addrtype;
-                       connected = 1;
-                       strncpy(hostname, hp->h_name, sizeof(hostname));
-                       hostname[sizeof(hostname)-1] = 0;
                }
                if (argc < 4) {
                        cp = argc == 3 ? argv[2] : tail(src);
@@ -461,7 +477,6 @@
                        if (verbose)
                                printf("getting from %s:%s to %s [%s]\n",
                                        hostname, src, cp, mode);
-                       peeraddr.sin_port = port;
                        recvfile(fd, src, mode);
                        break;
                }
@@ -474,7 +489,6 @@
                if (verbose)
                        printf("getting from %s:%s to %s [%s]\n",
                                hostname, src, cp, mode);
-               peeraddr.sin_port = port;
                recvfile(fd, src, mode);
        }
 }



Home | Main Index | Thread Index | Old Index