[BACK]Return to ftp.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / ftp

Diff for /src/usr.bin/ftp/ftp.c between version 1.33 and 1.34

version 1.33, 1998/12/13 21:01:29 version 1.34, 1999/12/08 12:57:06
Line 2 
Line 2 
 /*      $NetBSD: ftp.c,v 1.27 1997/08/18 10:20:23 lukem Exp $   */  /*      $NetBSD: ftp.c,v 1.27 1997/08/18 10:20:23 lukem Exp $   */
   
 /*  /*
    * Copyright (C) 1997 and 1998 WIDE Project.
    * All rights reserved.
    *
    * Redistribution and use in source and binary forms, with or without
    * modification, are permitted provided that the following conditions
    * are met:
    * 1. Redistributions of source code must retain the above copyright
    *    notice, this list of conditions and the following disclaimer.
    * 2. Redistributions in binary form must reproduce the above copyright
    *    notice, this list of conditions and the following disclaimer in the
    *    documentation and/or other materials provided with the distribution.
    * 3. Neither the name of the project nor the names of its contributors
    *    may be used to endorse or promote products derived from this software
    *    without specific prior written permission.
    *
    * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
    * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
    * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
    * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
    * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
    * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
    * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
    * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
    * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
    * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
    * SUCH DAMAGE.
    */
   
   /*
  * Copyright (c) 1985, 1989, 1993, 1994   * Copyright (c) 1985, 1989, 1993, 1994
  *      The Regents of the University of California.  All rights reserved.   *      The Regents of the University of California.  All rights reserved.
  *   *
Line 70 
Line 99 
   
 #include "ftp_var.h"  #include "ftp_var.h"
   
 struct  sockaddr_in hisctladdr;  union sockunion {
 struct  sockaddr_in data_addr;          struct sockinet {
                   u_char si_len;
                   u_char si_family;
                   u_short si_port;
           } su_si;
           struct sockaddr_in  su_sin;
           struct sockaddr_in6 su_sin6;
   };
   #define su_len          su_si.si_len
   #define su_family       su_si.si_family
   #define su_port         su_si.si_port
   
   union sockunion myctladdr, hisctladdr, data_addr;
   
   union sockunion hisctladdr;
   union sockunion data_addr;
 int     data = -1;  int     data = -1;
 int     abrtflag = 0;  int     abrtflag = 0;
 jmp_buf ptabort;  jmp_buf ptabort;
 int     ptabflg;  int     ptabflg;
 int     ptflag = 0;  int     ptflag = 0;
 struct  sockaddr_in myctladdr;  union sockunion myctladdr;
 off_t   restart_point = 0;  off_t   restart_point = 0;
   
   
Line 85 
Line 129 
   
 char *  char *
 hookup(host, port)  hookup(host, port)
         const char *host;          char *host;
         in_port_t port;          char *port;
 {  {
         struct hostent *hp = NULL;          int s, len, tos, error;
         int s, len, tos;  
         static char hostnamebuf[MAXHOSTNAMELEN];          static char hostnamebuf[MAXHOSTNAMELEN];
           struct addrinfo hints, *res, *res0;
           char hbuf[MAXHOSTNAMELEN];
           char *cause = "unknown";
   
         memset((void *)&hisctladdr, 0, sizeof(hisctladdr));          memset((char *)&hisctladdr, 0, sizeof (hisctladdr));
         if (inet_aton(host, &hisctladdr.sin_addr) != 0) {          memset(&hints, 0, sizeof(hints));
                 hisctladdr.sin_family = AF_INET;          hints.ai_flags = AI_CANONNAME;
                 (void)strncpy(hostnamebuf, host, sizeof(hostnamebuf) - 1);          hints.ai_family = AF_UNSPEC;
                 hostnamebuf[sizeof(hostnamebuf) - 1] = '\0';          hints.ai_socktype = SOCK_STREAM;
         } else {          hints.ai_protocol = 0;
                 hp = gethostbyname(host);          error = getaddrinfo(host, port, &hints, &res0);
                 if (hp == NULL) {          if (error) {
                         warnx("%s: %s", host, hstrerror(h_errno));                  warn(gai_strerror(error));
                         code = -1;  
                         return ((char *) 0);  
                 }  
                 hisctladdr.sin_family = hp->h_addrtype;  
                 memcpy(&hisctladdr.sin_addr, hp->h_addr_list[0],  
                     (size_t)hp->h_length);  
                 (void)strncpy(hostnamebuf, hp->h_name, sizeof(hostnamebuf) - 1);  
                 hostnamebuf[sizeof(hostnamebuf) - 1] = '\0';  
         }  
         hostname = hostnamebuf;  
         s = socket(hisctladdr.sin_family, SOCK_STREAM, 0);  
         if (s < 0) {  
                 warn("socket");  
                 code = -1;                  code = -1;
                 return (0);                  return (0);
         }          }
         hisctladdr.sin_port = port;  
         while (connect(s, (struct sockaddr *)&hisctladdr,  
                         sizeof(hisctladdr)) < 0) {  
                 if (errno == EINTR)  
                         continue;  
                 if (hp && hp->h_addr_list[1]) {  
                         int oerrno = errno;  
                         char *ia;  
   
                         ia = inet_ntoa(hisctladdr.sin_addr);          if (res0->ai_canonname)
                         errno = oerrno;                  strncpy(hostnamebuf, res0->ai_canonname, sizeof(hostnamebuf));
                         warn("connect to address %s", ia);          else
                         hp->h_addr_list++;                  strncpy(hostnamebuf, host, sizeof(hostnamebuf));
                         memcpy(&hisctladdr.sin_addr, hp->h_addr_list[0],          hostnamebuf[sizeof(hostnamebuf) - 1] = '\0';
                             (size_t)hp->h_length);          hostname = hostnamebuf;
                         fprintf(ttyout, "Trying %s...\n",  
                             inet_ntoa(hisctladdr.sin_addr));          s = -1;
                         (void)close(s);          for (res = res0; res; res = res->ai_next) {
                         s = socket(hisctladdr.sin_family, SOCK_STREAM, 0);  #if 0   /*old behavior*/
                         if (s < 0) {                  if (res != res0)        /* not on the first address */
                                 warn("socket");  #else
                                 code = -1;                  if (res0->ai_next)      /* if we have multiple possibilities */
                                 return (0);  #endif
                   {
                           getnameinfo(res->ai_addr, res->ai_addrlen,
                                   hbuf, sizeof(hbuf), NULL, 0, NI_NUMERICHOST);
                           fprintf(ttyout, "Trying %s...\n", hbuf);
                   }
                   s = socket(res->ai_family, res->ai_socktype, res->ai_protocol);
                   if (s < 0) {
                           cause = "socket";
                           continue;
                   }
                   while ((error = connect(s, res->ai_addr, res->ai_addrlen)) < 0
                                   && errno == EINTR) {
                           ;
                   }
                   if (error) {
                           /* this "if" clause is to prevent print warning twice */
                           if (res->ai_next) {
                                   getnameinfo(res->ai_addr, res->ai_addrlen,
                                           hbuf, sizeof(hbuf), NULL, 0,
                                           NI_NUMERICHOST);
                                   warn("connect to address %s", hbuf);
                         }                          }
                           cause = "connect";
                           close(s);
                           s = -1;
                         continue;                          continue;
                 }                  }
                 warn("connect");  
                   /* finally we got one */
                   break;
           }
           if (s < 0) {
                   warn(cause);
                 code = -1;                  code = -1;
                 goto bad;                  freeaddrinfo(res0);
                   return 0;
         }          }
         len = sizeof(myctladdr);          memcpy(&hisctladdr, res->ai_addr, res->ai_addrlen);
           len = res->ai_addrlen;
           freeaddrinfo(res0);
           res0 = res = NULL;
         if (getsockname(s, (struct sockaddr *)&myctladdr, &len) < 0) {          if (getsockname(s, (struct sockaddr *)&myctladdr, &len) < 0) {
                 warn("getsockname");                  warn("getsockname");
                 code = -1;                  code = -1;
                 goto bad;                  goto bad;
         }          }
 #ifdef IP_TOS  #if defined(IPPROTO_IP) && defined(IP_TOS)
         tos = IPTOS_LOWDELAY;          if (hisctladdr.su_family == AF_INET) {
         if (setsockopt(s, IPPROTO_IP, IP_TOS, (char *)&tos, sizeof(int)) < 0)                  tos = IPTOS_LOWDELAY;
                 warn("setsockopt TOS (ignored)");                  if (setsockopt(s, IPPROTO_IP, IP_TOS, (char *)&tos, sizeof(int)) < 0)
                           warn("setsockopt TOS (ignored)");
           }
 #endif  #endif
         cin = fdopen(s, "r");          cin = fdopen(s, "r");
         cout = fdopen(s, "w");          cout = fdopen(s, "w");
Line 334 
Line 394 
                         }                          }
                         if (dig < 4 && isdigit(c))                          if (dig < 4 && isdigit(c))
                                 code = code * 10 + (c - '0');                                  code = code * 10 + (c - '0');
                         if (!pflag && code == 227)                          if (!pflag && (code == 227 || code == 228))
                                 pflag = 1;                                  pflag = 1;
                           else if (!pflag && code == 229)
                                   pflag = 100;
                         if (dig > 4 && pflag == 1 && isdigit(c))                          if (dig > 4 && pflag == 1 && isdigit(c))
                                 pflag = 2;                                  pflag = 2;
                         if (pflag == 2) {                          if (pflag == 2) {
Line 346 
Line 408 
                                         pflag = 3;                                          pflag = 3;
                                 }                                  }
                         }                          }
                           if (pflag == 100 && c == '(')
                                   pflag = 2;
                         if (dig == 4 && c == '-') {                          if (dig == 4 && c == '-') {
                                 if (continuation)                                  if (continuation)
                                         code = 0;                                          code = 0;
Line 1112 
Line 1176 
         char *p, *a;          char *p, *a;
         int result, len, tmpno = 0;          int result, len, tmpno = 0;
         int on = 1;          int on = 1;
         int a0, a1, a2, a3, p0, p1;          int error;
           u_int addr[16], port[2];
           u_int af, hal, pal;
           char *pasvcmd = NULL;
   
           if (myctladdr.su_family == AF_INET6
            && (IN6_IS_ADDR_LINKLOCAL(&myctladdr.su_sin6.sin6_addr)
             || IN6_IS_ADDR_SITELOCAL(&myctladdr.su_sin6.sin6_addr))) {
                   warnx("use of scoped address can be troublesome");
           }
 reinit:  reinit:
         if (passivemode) {          if (passivemode) {
                 data = socket(AF_INET, SOCK_STREAM, 0);                  data_addr = myctladdr;
                   data = socket(data_addr.su_family, SOCK_STREAM, 0);
                 if (data < 0) {                  if (data < 0) {
                         warn("socket");                          warn("socket");
                         return (1);                          return (1);
Line 1125 
Line 1198 
                     setsockopt(data, SOL_SOCKET, SO_DEBUG, (char *)&on,                      setsockopt(data, SOL_SOCKET, SO_DEBUG, (char *)&on,
                                sizeof(on)) < 0)                                 sizeof(on)) < 0)
                         warn("setsockopt (ignored)");                          warn("setsockopt (ignored)");
                 if (command("PASV") != COMPLETE) {                  switch (data_addr.su_family) {
                   case AF_INET:
                           result = command(pasvcmd = "EPSV");
                           if (code / 10 == 22 && code != 229) {
                                   fputs(
   "wrong server: return code must be 229\n",
                                           ttyout);
                                   result = COMPLETE + 1;
                           }
                           if (result != COMPLETE)
                                   result = command(pasvcmd = "PASV");
                           break;
                   case AF_INET6:
                           result = command(pasvcmd = "EPSV");
                           if (code / 10 == 22 && code != 229) {
                                   fputs(
   "wrong server: return code must be 229\n",
                                           ttyout);
                                   result = COMPLETE + 1;
                           }
                           if (result != COMPLETE)
                                   result = command(pasvcmd = "LPSV");
                           break;
                   default:
                           result = COMPLETE + 1;
                           break;
                   }
                   if (result != COMPLETE) {
                         if (activefallback) {                          if (activefallback) {
                                 (void)close(data);                                  (void)close(data);
                                 data = -1;                                  data = -1;
Line 1137 
Line 1237 
                         goto bad;                          goto bad;
                 }                  }
   
   #define pack2(var, off) \
           (((var[(off) + 0] & 0xff) << 8) | ((var[(off) + 1] & 0xff) << 0))
   #define pack4(var, off) \
           (((var[(off) + 0] & 0xff) << 24) | ((var[(off) + 1] & 0xff) << 16) | \
            ((var[(off) + 2] & 0xff) << 8) | ((var[(off) + 3] & 0xff) << 0))
   
                 /*                  /*
                  * What we've got at this point is a string of comma                   * What we've got at this point is a string of comma separated
                  * separated one-byte unsigned integer values.                   * one-byte unsigned integer values, separated by commas.
                  * The first four are the an IP address. The fifth is  
                  * the MSB of the port number, the sixth is the LSB.  
                  * From that we'll prepare a sockaddr_in.  
                  */                   */
                   if (strcmp(pasvcmd, "PASV") == 0) {
                           if (data_addr.su_family != AF_INET) {
                                   fputs(
   "Passive mode AF mismatch. Shouldn't happen!\n", ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           if (code / 10 == 22 && code != 227) {
                                   fputs("wrong server: return code must be 227\n",
                                           ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           error = sscanf(pasv, "%u,%u,%u,%u,%u,%u",
                                           &addr[0], &addr[1], &addr[2], &addr[3],
                                           &port[0], &port[1]);
                           if (error != 6) {
                                   fputs(
   "Passive mode address scan failure. Shouldn't happen!\n", ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           error = 0;
                           memset(&data_addr, 0, sizeof(data_addr));
                           data_addr.su_family = AF_INET;
                           data_addr.su_len = sizeof(struct sockaddr_in);
                           data_addr.su_sin.sin_addr.s_addr =
                                   htonl(pack4(addr, 0));
                           data_addr.su_port = htons(pack2(port, 0));
                   } else if (strcmp(pasvcmd, "LPSV") == 0) {
                           if (code / 10 == 22 && code != 228) {
                                   fputs("wrong server: return code must be 228\n",
                                           ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           switch (data_addr.su_family) {
                           case AF_INET:
                                   error = sscanf(pasv,
   "%u,%u,%u,%u,%u,%u,%u,%u,%u",
                                           &af, &hal,
                                           &addr[0], &addr[1], &addr[2], &addr[3],
                                           &pal, &port[0], &port[1]);
                                   if (error != 9) {
                                           fputs(
   "Passive mode address scan failure. Shouldn't happen!\n", ttyout);
                                           error = 1;
                                           goto bad;
                                   }
                                   if (af != 4 || hal != 4 || pal != 2) {
                                           fputs(
   "Passive mode AF mismatch. Shouldn't happen!\n", ttyout);
                                           error = 1;
                                           goto bad;
                                   }
   
                 if (sscanf(pasv, "%d,%d,%d,%d,%d,%d",                                  error = 0;
                            &a0, &a1, &a2, &a3, &p0, &p1) != 6) {                                  memset(&data_addr, 0, sizeof(data_addr));
                         fputs(                                  data_addr.su_family = AF_INET;
                                   data_addr.su_len = sizeof(struct sockaddr_in);
                                   data_addr.su_sin.sin_addr.s_addr =
                                           htonl(pack4(addr, 0));
                                   data_addr.su_port = htons(pack2(port, 0));
                                   break;
                           case AF_INET6:
                                   error = sscanf(pasv,
   "%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u",
                                           &af, &hal,
                                           &addr[0], &addr[1], &addr[2], &addr[3],
                                           &addr[4], &addr[5], &addr[6], &addr[7],
                                           &addr[8], &addr[9], &addr[10],
                                           &addr[11], &addr[12], &addr[13],
                                           &addr[14], &addr[15],
                                           &pal, &port[0], &port[1]);
                                   if (error != 21) {
                                           fputs(
 "Passive mode address scan failure. Shouldn't happen!\n", ttyout);  "Passive mode address scan failure. Shouldn't happen!\n", ttyout);
                         goto bad;                                          error = 1;
                 }                                          goto bad;
                                   }
                                   if (af != 6 || hal != 16 || pal != 2) {
                                           fputs(
   "Passive mode AF mismatch. Shouldn't happen!\n", ttyout);
                                           error = 1;
                                           goto bad;
                                   }
   
                 memset(&data_addr, 0, sizeof(data_addr));                                  error = 0;
                 data_addr.sin_family = AF_INET;                                  memset(&data_addr, 0, sizeof(data_addr));
                 a = (char *)&data_addr.sin_addr.s_addr;                                  data_addr.su_family = AF_INET6;
                 a[0] = a0 & 0xff;                                  data_addr.su_len = sizeof(struct sockaddr_in6);
                 a[1] = a1 & 0xff;                              {
                 a[2] = a2 & 0xff;                                  u_int32_t *p32;
                 a[3] = a3 & 0xff;                                  p32 = (u_int32_t *)&data_addr.su_sin6.sin6_addr;
                 p = (char *)&data_addr.sin_port;                                  p32[0] = htonl(pack4(addr, 0));
                 p[0] = p0 & 0xff;                                  p32[1] = htonl(pack4(addr, 4));
                 p[1] = p1 & 0xff;                                  p32[2] = htonl(pack4(addr, 8));
                                   p32[3] = htonl(pack4(addr, 12));
                               }
                                   data_addr.su_port = htons(pack2(port, 0));
                                   break;
                           default:
                                   error = 1;
                           }
                   } else if (strcmp(pasvcmd, "EPSV") == 0) {
                           char delim[4];
   
                           port[0] = 0;
                           if (code / 10 == 22 && code != 229) {
                                   fputs("wrong server: return code must be 229\n",
                                           ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           if (sscanf(pasv, "%c%c%c%d%c", &delim[0],
                                           &delim[1], &delim[2], &port[1],
                                           &delim[3]) != 5) {
                                   fputs("parse error!\n", ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           if (delim[0] != delim[1] || delim[0] != delim[2]
                            || delim[0] != delim[3]) {
                                   fputs("parse error!\n", ttyout);
                                   error = 1;
                                   goto bad;
                           }
                           data_addr = hisctladdr;
                           data_addr.su_port = htons(port[1]);
                   } else
                           goto bad;
   
                 while (connect(data, (struct sockaddr *)&data_addr,                  while (connect(data, (struct sockaddr *)&data_addr,
                             sizeof(data_addr)) < 0) {                              data_addr.su_len) < 0) {
                         if (errno == EINTR)                          if (errno == EINTR)
                                 continue;                                  continue;
                         if (activefallback) {                          if (activefallback) {
Line 1177 
Line 1393 
                         warn("connect");                          warn("connect");
                         goto bad;                          goto bad;
                 }                  }
 #ifdef IP_TOS  #if defined(IPPROTO_IP) && defined(IP_TOS)
                 on = IPTOS_THROUGHPUT;                  if (data_addr.su_family == AF_INET) {
                 if (setsockopt(data, IPPROTO_IP, IP_TOS, (char *)&on,                          on = IPTOS_THROUGHPUT;
                                sizeof(int)) < 0)                          if (setsockopt(data, IPPROTO_IP, IP_TOS, (char *)&on,
                         warn("setsockopt TOS (ignored)");                                         sizeof(int)) < 0)
                                   warn("setsockopt TOS (ignored)");
                   }
 #endif  #endif
                 return (0);                  return (0);
         }          }
Line 1189 
Line 1407 
 noport:  noport:
         data_addr = myctladdr;          data_addr = myctladdr;
         if (sendport)          if (sendport)
                 data_addr.sin_port = 0; /* let system pick one */                  data_addr.su_port = 0;  /* let system pick one */
         if (data != -1)          if (data != -1)
                 (void)close(data);                  (void)close(data);
         data = socket(AF_INET, SOCK_STREAM, 0);          data = socket(data_addr.su_family, SOCK_STREAM, 0);
         if (data < 0) {          if (data < 0) {
                 warn("socket");                  warn("socket");
                 if (tmpno)                  if (tmpno)
Line 1205 
Line 1423 
                         warn("setsockopt (reuse address)");                          warn("setsockopt (reuse address)");
                         goto bad;                          goto bad;
                 }                  }
         if (bind(data, (struct sockaddr *)&data_addr, sizeof(data_addr)) < 0) {          if (bind(data, (struct sockaddr *)&data_addr, data_addr.su_len) < 0) {
                 warn("bind");                  warn("bind");
                 goto bad;                  goto bad;
         }          }
Line 1220 
Line 1438 
         }          }
         if (listen(data, 1) < 0)          if (listen(data, 1) < 0)
                 warn("listen");                  warn("listen");
         if (sendport) {  
                 a = (char *)&data_addr.sin_addr;  
                 p = (char *)&data_addr.sin_port;  
 #define UC(b)   (((int)b)&0xff)  #define UC(b)   (((int)b)&0xff)
                 result =  
                     command("PORT %d,%d,%d,%d,%d,%d",          if (sendport) {
                       UC(a[0]), UC(a[1]), UC(a[2]), UC(a[3]),                  char hname[INET6_ADDRSTRLEN];
                       UC(p[0]), UC(p[1]));                  int af;
   
                   switch (data_addr.su_family) {
                   case AF_INET:
                   case AF_INET6:
                           af = (data_addr.su_family == AF_INET) ? 1 : 2;
                           if (getnameinfo((struct sockaddr *)&data_addr,
                                           data_addr.su_len, hname, sizeof(hname),
                                           NULL, 0, NI_NUMERICHOST)) {
                                   result = ERROR;
                           } else {
                                   result = command("EPRT |%d|%s|%d|",
                                           af, hname, ntohs(data_addr.su_port));
                           }
                           break;
                   default:
                           result = COMPLETE + 1;
                           break;
                   }
                   if (result == COMPLETE)
                           goto skip_port;
   
                   switch (data_addr.su_family) {
                   case AF_INET:
                           a = (char *)&data_addr.su_sin.sin_addr;
                           p = (char *)&data_addr.su_port;
                           result = command("PORT %d,%d,%d,%d,%d,%d",
                                    UC(a[0]), UC(a[1]), UC(a[2]), UC(a[3]),
                                    UC(p[0]), UC(p[1]));
                           break;
                   case AF_INET6:
                           a = (char *)&data_addr.su_sin6.sin6_addr;
                           p = (char *)&data_addr.su_port;
                           result = command(
   "LPRT %d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d",
                                    6, 16,
                                    UC(a[0]),UC(a[1]),UC(a[2]),UC(a[3]),
                                    UC(a[4]),UC(a[5]),UC(a[6]),UC(a[7]),
                                    UC(a[8]),UC(a[9]),UC(a[10]),UC(a[11]),
                                    UC(a[12]),UC(a[13]),UC(a[14]),UC(a[15]),
                                    2, UC(p[0]), UC(p[1]));
                           break;
                   default:
                           result = COMPLETE + 1; /* xxx */
                   }
           skip_port:
   
                 if (result == ERROR && sendport == -1) {                  if (result == ERROR && sendport == -1) {
                         sendport = 0;                          sendport = 0;
                         tmpno = 1;                          tmpno = 1;
Line 1237 
Line 1499 
         }          }
         if (tmpno)          if (tmpno)
                 sendport = 1;                  sendport = 1;
 #ifdef IP_TOS  #if defined(IPPROTO_IP) && defined(IP_TOS)
         on = IPTOS_THROUGHPUT;          if (data_addr.su_family == AF_INET) {
         if (setsockopt(data, IPPROTO_IP, IP_TOS, (char *)&on, sizeof(int)) < 0)                  on = IPTOS_THROUGHPUT;
                 warn("setsockopt TOS (ignored)");                  if (setsockopt(data, IPPROTO_IP, IP_TOS, (char *)&on,
                                  sizeof(int)) < 0)
                           warn("setsockopt TOS (ignored)");
           }
 #endif  #endif
         return (0);          return (0);
 bad:  bad:
Line 1254 
Line 1519 
 dataconn(lmode)  dataconn(lmode)
         const char *lmode;          const char *lmode;
 {  {
         struct sockaddr_in from;          union sockunion from;
         int s, fromlen, tos;          int s, fromlen = myctladdr.su_len;
   
         fromlen = sizeof(from);  
   
         if (passivemode)          if (passivemode)
                 return (fdopen(data, lmode));                  return (fdopen(data, lmode));
   
Line 1270 
Line 1533 
         }          }
         (void)close(data);          (void)close(data);
         data = s;          data = s;
 #ifdef IP_TOS  #if defined(IPPROTO_IP) && defined(IP_TOS)
         tos = IPTOS_THROUGHPUT;          if (from.su_family == AF_INET) {
         if (setsockopt(s, IPPROTO_IP, IP_TOS, (char *)&tos, sizeof(int)) < 0)                  int tos = IPTOS_THROUGHPUT;
                 warn("setsockopt TOS (ignored)");                  if (setsockopt(s, IPPROTO_IP, IP_TOS, (char *)&tos,
                                   sizeof(int)) < 0) {
                           warn("setsockopt TOS (ignored)");
                   }
           }
 #endif  #endif
         return (fdopen(data, lmode));          return (fdopen(data, lmode));
 }  }
Line 1306 
Line 1573 
         static struct comvars {          static struct comvars {
                 int connect;                  int connect;
                 char name[MAXHOSTNAMELEN];                  char name[MAXHOSTNAMELEN];
                 struct sockaddr_in mctl;                  union sockunion mctl;
                 struct sockaddr_in hctl;                  union sockunion hctl;
                 FILE *in;                  FILE *in;
                 FILE *out;                  FILE *out;
                 int tpe;                  int tpe;

Legend:
Removed from v.1.33  
changed lines
  Added in v.1.34