imported 9.0.299 Beta.01
[ckermit.git] / ckcnet.c
index 3bae53e..5384e00 100644 (file)
--- a/ckcnet.c
+++ b/ckcnet.c
@@ -1,9 +1,9 @@
-char *cknetv = "Network support, 8.0.283, 7 Feb 2004";
+char *cknetv = "Network support, 9.0.296, 16 Mar 2010";
 
 /*  C K C N E T  --  Network support  */
 
 /*
-  Copyright (C) 1985, 2004,
+  Copyright (C) 1985, 2010,
     Trustees of Columbia University in the City of New York.
     All rights reserved.  See the C-Kermit COPYING.TXT file or the
     copyright text in the ckcmai.c module for disclaimer and permissions.
@@ -72,8 +72,15 @@ char *cknetv = "Network support, 8.0.283, 7 Feb 2004";
 #ifdef USE_NAMESER_COMPAT
 #include <arpa/nameser_compat.h>
 #endif /* USE_NAMESER_COMPAT */
+
+#ifdef MINIX3
+#include <net/gen/resolv.h>
+#include <net/gen/nameser.h>
+#else
 #include <arpa/nameser.h>
 #include <resolv.h>
+#endif /* MINIX 3 */
+
 #ifndef PS2AIX10
 #ifndef BSD4
 #ifndef I386IX
@@ -138,10 +145,22 @@ extern int inserver;
 #endif /* IKSD */
 
 char myipaddr[20] = { '\0' };           /* Global copy of my IP address */
+char hostipaddr[64] = { '\0' };                /* Global copy of remote IP address */
 
 #ifdef NETCONN
 /* Don't need any of this if there is no network support. */
 
+#ifndef OS2
+/* Current fd-swapping hack is not thread-safe */
+#define HTTP_BUFFERING
+#endif /* OS2 */
+
+#ifdef HTTP_BUFFERING
+#define HTTP_INBUFLEN 8192
+static char http_inbuf[HTTP_INBUFLEN];
+static int http_bufp = 0, http_count;
+#endif /* HTTP_BUFFERING */
+
 /*
   NETLEBUF is (must be) defined for those platforms that call this
   module to do network i/o (e.g. netinc(), nettchk(), etc) rather
@@ -182,7 +201,9 @@ int tt_push_inited = 0;
 
 #ifdef HPUX
 #ifndef HPUX7                           /* HPUX 7.00 doesn't have it */
+#ifndef HPUX6                           /* HPUX 6.00 doesn't have it */
 #include <arpa/inet.h>                  /* For inet_ntoa() prototype */
+#endif /* HPUX6 */
 #endif /* HPUX7 */
 #endif /* HPUX */
 
@@ -580,7 +601,7 @@ le_puts(s,n) CHAR * s; int n;
     int rc = 0;
     int i = 0;
     CHAR * p = (CHAR *)"le_puts";
-    hexdump(p,s,n);
+    ckhexdump(p,s,n);
     for (i = 0; i < n; i++)
       rc = le_putchar((char)s[i]);
     debug(F101,"le_puts","",rc);
@@ -597,7 +618,7 @@ le_putstr(s) CHAR * s;
     CHAR * p;
     int rc = 0;
     p = (CHAR *)"le_putstr";
-    hexdump(p,s,(int)strlen((char *)s));
+    ckhexdump(p,s,(int)strlen((char *)s));
     for (p = s; *p && !rc; p++)
       rc = le_putchar(*p);
     return(rc);
@@ -1279,7 +1300,7 @@ ttbufr() {                              /* TT Buffer Read */
               return(-2);
 #endif /* OS2ONLY */
           } else {                      /* we got out-of-band data */
-              hexdump("ttbufr out-of-band chars",&ttibuf[ttibp+ttibn],count);
+              ckhexdump("ttbufr out-of-band chars",&ttibuf[ttibp+ttibn],count);
 #ifdef BETADEBUG
               bleep(BP_NOTE);
 #endif /* BETADEBUG */
@@ -1561,8 +1582,11 @@ inet_ntoa(in) struct in_addr in; {
 
 int ucx_port_bug = 0;                   /* Explained below */
 
-#ifndef __DECC                          /* VAXC or GCC */
-
+#ifdef OLDIP                           /* Very old VAXC or GCC */
+/*
+  Note that my oldest VAX C (V3.1-051) does not need (or want) OLDIP,
+  hence the "Very old" in the comment - SMS, 2010/03/15.
+*/
 #define getservbyname my_getservbyname
 
 #ifdef CK_ANSIC
@@ -1638,9 +1662,15 @@ my_getservbyname (service, proto) char *service, *proto; {
     }
     return &sent;
 }
-#endif /* __DECC */
+#endif /* def OLDIP */
 #endif /* DEC_TCPIP */
 #endif /* EXCELAN */
+
+int
+gettcpport() {
+    return(svcnum);
+}
+
 #endif /* TCPSOCKET */
 
 #ifndef NOTCPOPTS
@@ -2418,8 +2448,17 @@ tcpsocket_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo {
 
     netclos();                          /* Close any previous connection. */
     ckstrncpy(namecopy, name, NAMECPYL); /* Copy the hostname. */
+#ifdef COMMENT
+    /* Jeff's version from 30 Dec 2005 doesn't inhibit Telnet */
+    if (ttnproto != NP_TCPRAW &&
+       ttnproto != NP_SSL_RAW &&
+       ttnproto != NP_TLS_RAW)
+      ttnproto = NP_NONE;               /* No protocol selected yet. */
+#else
+    /* fdc's version from 4 Dec 2005 works ok */
     if (ttnproto != NP_TCPRAW)
       ttnproto = NP_NONE;               /* No protocol selected yet. */
+#endif /* COMMENT */
     debug(F110,"tcpsocket_open namecopy",namecopy,0);
 
     /* Assign the socket number to ttyfd and then fill in tcp structures */
@@ -2525,8 +2564,16 @@ tcpsocket_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo {
     else
 #endif /* RLOGCODE */
     /* Assume the service is TELNET. */
-    if (ttnproto != NP_TCPRAW)
-        ttnproto = NP_TELNET;           /* Yes, set global flag. */
+#ifdef COMMENT
+      /* Jeff's code from 2005/12/30 */
+      if (ttnproto != NP_TCP_RAW &&
+         ttnproto != NP_SSL_RAW &&
+         ttnproto != NP_TLS_RAW)
+#else
+      /* fdc's code from 2005/12/04 */
+      if (ttnproto != NP_TCPRAW)
+#endif /* COMMENT */
+       ttnproto = NP_TELNET;           /* Yes, set global flag. */
 #ifdef CK_SECURITY
     /* Before Initialization Telnet/Rlogin Negotiations Init Kerberos */
     ck_auth_init((tcp_rdns && host && host->h_name && host->h_name[0]) ?
@@ -2594,10 +2641,18 @@ tcpsrv_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo; {
 
     netclos();                          /* Close any previous connection. */
     ckstrncpy(namecopy, name, NAMECPYL); /* Copy the hostname. */
-#ifdef COMMENT
     /* Don't do this. */
+#ifdef COMMENT
+    /* fdc */
     if (ttnproto != NP_TCPRAW)
       ttnproto = NP_NONE;               /* No protocol selected yet. */
+#endif /* COMMENT */
+#ifdef COMMENT
+    /* Jeff */
+    if (ttnproto != NP_TCP_RAW &&
+       ttnproto != NP_SSL_RAW &&
+       ttnproto != NP_TLS_RAW)
+      ttnproto = NP_NONE;               /* No protocol selected yet. */
 #endif /* COMMENT */
     debug(F110,"tcpsrv_open namecopy",namecopy,0);
 
@@ -2799,7 +2854,11 @@ tcpsrv_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo; {
 #endif /* HPUX1010 */
 #else
 #ifdef __DECC
+#ifdef INTSELECT
+                       (int *)
+#else /* def INTSELECT */
                        (fd_set *)
+#endif /* def INTSELECT [else] */
 #endif /* __DECC */
 #endif /* HPUX */
                        &rfds, NULL, NULL, &tv) > 0) &&
@@ -2887,10 +2946,17 @@ tcpsrv_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo; {
         x = (unsigned short)service->s_port;
         service2 = getservbyname("telnet", "tcp");
         if (service2 && x == service2->s_port) {
+#ifdef COMMENT
+           /* Jeff 2005/12/30 */
+           if (ttnproto != NP_TCPRAW && /* Yes... */
+                ttnproto != NP_SSL_RAW &&
+                ttnproto != NP_TLS_RAW) /* and if raw port not requested */
+#else
+           /* fdc 2005/12/04 */
             if (ttnproto != NP_TCPRAW)  /* Yes and if raw port not requested */
-              ttnproto = NP_TELNET;     /* Set protocol to TELNET. */
+#endif /*  */
+              ttnproto = NP_TELNET;    /* set protocol to TELNET. */
         }
-
         ckstrncpy(ipaddr,(char *)inet_ntoa(saddr.sin_addr),20);
         if (tcp_rdns) {
             if (!quiet) {
@@ -2906,8 +2972,8 @@ tcpsrv_open(name,lcl,nett,timo) char * name; int * lcl; int nett; int timo; {
                 }
                 name[0] = '*';
                 ckstrncpy(&name[1],host->h_name,78);
-                strncat(name,":",80-strlen(name));
-                strncat(name,p,80-strlen(name));
+                ckstrncat(name,":",80-strlen(name));
+                ckstrncat(name,p,80-strlen(name));
                 if (!quiet
 #ifndef NOICP
                     && !doconx
@@ -3089,6 +3155,9 @@ ckgetpeer() {
     static char namebuf[256];
     static struct hostent *host;
     static struct sockaddr_in saddr;
+#ifdef GPEERNAME_T
+    static GPEERNAME_T saddrlen;
+#else
 #ifdef PTX
     static size_t saddrlen;
 #else
@@ -3101,13 +3170,34 @@ ckgetpeer() {
     static size_t saddrlen;
 #else  /* UNIXWARE */
 #ifdef DEC_TCPIP
+/* 2010-03-08 SMS.
+ * Coincidentally, the condition for integer arguments in select(),
+ * which is actually "defined( _DECC_V4_SOURCE)", works for an integer
+ * argument in getpeername().  Sadly, due to a lack of foresight,
+ * "defined( _DECC_V4_SOURCE)" doesn't work with DEC C V4.0, so the
+ * user-specified INTSELECT is used instead.  Most likely, "size_t"
+ * should be used instead of "unsigned int", but I'm a coward.
+ */
+#ifdef INTSELECT
+    static int saddrlen;
+#else /* def INTSELECT */
     static unsigned int saddrlen;
+#endif /* def INTSELECT [else] */
+#else
+#ifdef MACOSX10
+    static unsigned int saddrlen;
+#else
+#ifdef CK_64BIT
+    static socklen_t saddrlen;
 #else
     static int saddrlen;
-#endif /* VMS */
+#endif /* CK_64BIT */
+#endif /* MACOSX10 */
+#endif /* DEC_TCPIP */
 #endif /* UNIXWARE */
 #endif /* AIX42 */
 #endif /* PTX */
+#endif /* GPEERNAME_T */
     saddrlen = sizeof(saddr);
     if (getpeername(ttyfd,(struct sockaddr *)&saddr,&saddrlen) < 0) {
         debug(F111,"ckgetpeer failure",ckitoa(ttyfd),errno);
@@ -3179,11 +3269,13 @@ ckgetfqhostname(name) char * name;
 #else  /* HADDRLIST */
         bcopy(host->h_addr, (caddr_t)&r_addr.sin_addr, host->h_length);
 #endif /* HADDRLIST */
+#ifdef COMMENT
 #ifndef EXCELAN
         debug(F111,"BCOPY","host->h_addr",host->h_addr);
 #endif /* EXCELAN */
         debug(F111,"BCOPY"," (caddr_t)&r_addr.sin_addr",
               (caddr_t)&r_addr.sin_addr);
+#endif /* COMMENT */
         debug(F111,"BCOPY","host->h_length",host->h_length);
 
 #ifdef NT
@@ -3208,7 +3300,7 @@ ckgetfqhostname(name) char * name;
 #endif /* HADDRLIST */
 
     if (i > 0)
-      strncat(namebuf,&name[i-1],256-strlen(namebuf)-strlen(&name[i-1]));
+      ckstrncat(namebuf,&name[i-1],256-strlen(namebuf)-strlen(&name[i-1]));
     debug(F110,"ckgetfqhn()",namebuf,0);
     return(namebuf);
 #endif /* NOCKGETFQHOST */
@@ -3235,7 +3327,7 @@ setnproto(p) char * p;
 #ifdef CK_SSL
         /* Commonly used SSL ports (might not be in services file) */
         else if (!strcmp("https",p)) {
-          ttnproto = NP_SSL;
+          ttnproto = NP_SSL_RAW;
           ssl_only_flag = 1;
         } else if (!strcmp("ssl-telnet",p)) {
           ttnproto = NP_TELNET;
@@ -3279,7 +3371,13 @@ setnproto(p) char * p;
             break;
 #ifdef CK_SSL
           case 443:
+#ifdef COMMENT
+           /* Jeff 2005/12/30 */
+            ttnproto = NP_SSL_RAW;
+#else
+           /* fdc 2005/12/04 */
             ttnproto = NP_SSL;
+#endif /* COMMENT */
             ssl_only_flag = 1;
             break;
           case 151:
@@ -3424,10 +3522,13 @@ ckgetservice(hostname, servicename, ip, iplen)
   type rather than modem type.  Designed to be called from within ttopen.
 */
 
+#define XXNAMELEN 256
+static char xxname[XXNAMELEN];
+
 int
 netopen(name, lcl, nett) char *name; int *lcl, nett; {
     char *p;
-    int i, x, dns = 0;
+    int i, x, rc_inet_addr = 0, dns = 0;
 #ifdef TCPSOCKET
     int isconnect = 0;
 #ifdef SO_OOBINLINE
@@ -4045,33 +4146,46 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
     iax.s_addr = inet_addr(namecopy);
     debug(F111,"netopen inet_addr",namecopy,iax.s_addr);
 #else /* INADDR_NONE */
+#ifdef SOLARIS
+    /* In Solaris inet_addr() is of type in_addr_t which is uint32_t */
+    /* (unsigned) yet it returns -1 (signed) on failure. */
+    /* It makes a difference in 64-bit builds. */
+    rc_inet_addr = inet_addr(namecopy);        /* Assign return code to an int */
+    iax = (unsigned) rc_inet_addr;     /* and from there to whatever.. */
+#else
 #ifndef datageneral
     iax = (unsigned int) inet_addr(namecopy);
 #else
     iax = -1L;
 #endif /* datageneral */
+#endif /* SOLARIS */
+    debug(F111,"netopen rc_inet_addr",namecopy,rc_inet_addr);
     debug(F111,"netopen inet_addr",namecopy,iax);
 #endif /* INADDR_NONE */
 #endif /* INADDRX */
 
     dns = 0;
     if (
-#ifdef INADDR_NONE
 /* This might give warnings on 64-bit platforms but they should be harmless */
 /* because INADDR_NONE should be all 1's anyway, thus the OR part is */
 /* probably superfluous -- not sure why it's even there, maybe it should be */
 /* removed. */
-        iax.s_addr == INADDR_NONE || iax.s_addr == (unsigned long) -1L
+#ifdef SOLARIS
+       rc_inet_addr == -1
+#else
+#ifdef INADDR_NONE
+        iax.s_addr == INADDR_NONE /* || iax.s_addr == (unsigned long) -1L */
 #else /* INADDR_NONE */
         iax < 0
 #endif /* INADDR_NONE */
+#endif /* SOLARIS */
         ) {
         if (!quiet) {
             printf(" DNS Lookup... ");
             fflush(stdout);
         }
         if ((host = gethostbyname(namecopy)) != NULL) {
-            debug(F100,"netopen gethostbyname != NULL","",0);
+            debug(F110,"netopen gethostbyname != NULL",namecopy,0);
             host = ck_copyhostent(host);
             dns = 1;                    /* Remember we performed dns lookup */
             r_addr.sin_family = host->h_addrtype;
@@ -4079,13 +4193,25 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
 #ifndef NOHTTP
                  && (tcp_http_proxy == NULL)
 #endif /* NOHTTP */
-                 ) {                   /* Copying into our argument? */
+               ) {
+#ifdef COMMENT
+                ckstrncpy(xxname,host->h_name,XXNAMELEN);
+               debug(F110,"netopen xxname[1]",xxname,0);
+                if ((XXNAMELEN - (int)strlen(name)) > ((int)strlen(svcbuf)+1)){
+                    ckstrncat(xxname,":",XXNAMELEN - (int)strlen(xxname));
+                    ckstrncat(xxname,svcbuf,XXNAMELEN - (int)strlen(xxname));
+                   debug(F110,"netopen xxname[2]",xxname,0);
+                }
+               name = (char *)xxname;
+#else
                 ckstrncpy(name,host->h_name,80);  /* Bad Bad Bad */
                 if ( (80-strlen(name)) > (strlen(svcbuf)+1) ) {
-                    strncat(name,":",80-strlen(name));
-                    strncat(name,svcbuf,80-strlen(name));
+                    ckstrncat(name,":",80-strlen(name));
+                    ckstrncat(name,svcbuf,80-strlen(name));
                 }
+#endif /* COMMENT */
             }
+           debug(F110,"netopen name after lookup",name,0);
 
 #ifdef HADDRLIST
 #ifdef h_addr
@@ -4100,20 +4226,22 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
             bcopy(host->h_addr, (caddr_t)&r_addr.sin_addr, host->h_length);
 #endif /* h_addr */
 #else  /* HADDRLIST */
+#ifdef HPUX6
+           r_addr.sin_addr.s_addr = (u_long)host->h_addr;
+#else  /* HPUX6 */
             bcopy(host->h_addr, (caddr_t)&r_addr.sin_addr, host->h_length);
+#endif /* HPUX6 */
 #endif /* HADDRLIST */
-#ifndef EXCELAN
-            debug(F111,"BCOPY","host->h_addr",host->h_addr);
-#endif /* EXCELAN */
-            debug(F111,"BCOPY"," (caddr_t)&r_addr.sin_addr",
-                  (caddr_t)&r_addr.sin_addr);
-            debug(F111,"BCOPY"," r_addr.sin_addr.s_addr",
-                  r_addr.sin_addr.s_addr);
+
+#ifndef HPUX6
             debug(F111,"BCOPY","host->h_length",host->h_length);
+#endif /* HPUX6 */
         }
     }
 #endif /* NOMHHOST */
 
+    debug(F101,"netopen dns","",dns);
+
     if (!dns) {
 #ifdef INADDRX
 /* inet_addr() is of type struct in_addr */
@@ -4530,7 +4658,14 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
     /* See if the service is TELNET. */
     if (x == TELNET_PORT) {
         /* Yes, so if raw port not requested */
+#ifdef COMMENT
+       /* Jeff 2005/12/30 */
+        if (ttnproto != NP_TCPRAW && ttnproto != NP_SSL_RAW && 
+           ttnproto != NP_TLS_RAW && ttnproto != NP_NONE)
+#else
+       /* fdc 2005/12/04 */
         if (ttnproto != NP_TCPRAW && ttnproto != NP_NONE)
+#endif /* COMMENT */
           ttnproto = NP_TELNET;         /* Select TELNET protocol. */
     }
 #ifdef RLOGCODE
@@ -4795,8 +4930,8 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
             if (*s) {                   /* Copying into our argument? */
                 ckstrncpy(name,s,80);   /* Bad Bad Bad */
                 if ( (80-strlen(name)) > (strlen(svcbuf)+1) ) {
-                    strncat(name,":",80-strlen(name));
-                    strncat(name,svcbuf,80-strlen(name));
+                    ckstrncat(name,":",80-strlen(name));
+                    ckstrncat(name,svcbuf,80-strlen(name));
                 }
             }
             if (!quiet && *s
@@ -4922,6 +5057,8 @@ _PROTOTYP(SIGTYP x25oobh, (int) );
 
     debug(F101,"netopen service","",svcnum);
     debug(F110,"netopen name",name,0);
+    debug(F110,"netopen ipaddr",ipaddr,0);
+    ckstrncpy(hostipaddr,ipaddr,63);
 
     if (lcl) if (*lcl < 0)              /* Local mode. */
       *lcl = 1;
@@ -4980,7 +5117,14 @@ netclos() {
 #endif /* VMS */
 #ifdef TNCODE
           if (ttnproto == NP_TELNET) {
-            if ( !TELOPT_ME(TELOPT_LOGOUT) ) {
+            if (!TELOPT_ME(TELOPT_LOGOUT)
+#ifdef COMMENT
+/* Jeff 2005/12/30 */
+#ifdef CK_SSL
+                && !ssl_raw_flag && !tls_raw_flag
+#endif /* CK_SSL */
+#endif /* COMMENT */
+               ) {
                /* Send LOGOUT option before close */
                if (tn_sopt(DO,TELOPT_LOGOUT) >= 0) {
                    TELOPT_UNANSWERED_DO(TELOPT_LOGOUT) = 1;
@@ -5562,12 +5706,12 @@ nettchk() {                             /* for reading from network */
         if (x >= 1) {                   /* Oops, actually got a byte? */
 #ifdef OS2
             /* In OS/2 we read directly into ttibuf[] */
-            hexdump("nettchk got real data",&ttibuf[ttibp+ttibn],x);
+            ckhexdump("nettchk got real data",&ttibuf[ttibp+ttibn],x);
             ttibn += x;
 #else /* OS2 */
 #ifdef CK_SSL
            if ( ssl_active_flag || tls_active_flag ) {
-               hexdump("nettchk got real data",&ttibuf[ttibp+ttibn],x);
+               ckhexdump("nettchk got real data",&ttibuf[ttibp+ttibn],x);
                ttibn += x;
            } else 
 #endif /* CK_SSL */
@@ -5722,7 +5866,7 @@ netxin(n,buf) int n; CHAR * buf; {
 #ifdef KRB5
 #ifdef RLOGCODE
     if (ttnproto == NP_EK5LOGIN) {
-        if ((len = krb5_des_read(ttyfd,buf,n,0)) < 0)
+        if ((len = krb5_des_read(ttyfd,(char *)buf,n,0)) < 0)
           return(-1);
         else
           return(len);
@@ -5730,7 +5874,7 @@ netxin(n,buf) int n; CHAR * buf; {
 #endif /* RLOGCODE */
 #ifdef KRB5_U2U
     if (ttnproto == NP_K5U2U) {
-        if ((len = krb5_u2u_read(ttyfd,buf,n)) < 0)
+        if ((len = krb5_u2u_read(ttyfd,(char *)buf,n)) < 0)
           return(-1);
         else
           return(len);
@@ -5984,9 +6128,15 @@ netinc(timo) int timo; {
                 WSASafeToCancel = 1;
 #endif /* NT */
                 rc = select(FD_SETSIZE,
-#ifndef __DECC
+#ifdef __DECC
+#ifdef INTSELECT
+                            (int *)
+#else /* def INTSELECT */
                             (fd_set *)
-#endif /* __DECC */
+#endif /* def INTSELECT [else] */
+#else /* def __DECC */
+                            (fd_set *)
+#endif /* def __DECC [else] */
                             &rfds, NULL, NULL, &tv);
                 if (rc < 0) {
                     int s_errno = socket_errno;
@@ -6138,7 +6288,7 @@ netinc(timo) int timo; {
                     extern int tt_type_mode;
                     if ( !ISVTNT(tt_type_mode) )
 #endif /* OS2 */
-                    hexdump("netinc &ttbuf[ttibp]",&ttibuf[ttibp],ttibn);
+                    ckhexdump("netinc &ttbuf[ttibp]",&ttibuf[ttibp],ttibn);
                 }
 #endif /* BETADEBUG */
             }
@@ -6179,7 +6329,7 @@ nettol(s,n) CHAR *s; int n; {
     }
     debug(F101,"nettol TCPIPLIB ttnet","",ttnet);
 #ifdef COMMENT
-    hexdump("nettol",s,n);
+    ckhexdump("nettol",s,n);
 #endif /* COMMENT */
 
 #ifdef CK_KERBEROS
@@ -6825,6 +6975,7 @@ getlocalipaddr() {
     /* if still not resolved, then try second strategy */
     /* This second strategy does not work on Windows */
 
+    debug(F100,"getlocalipaddr","",0);
     memset(&l_sa,0,slen);
     memset(&r_sa,0,slen);
 
@@ -6885,6 +7036,7 @@ getlocalipaddrs(buf,bufsz,index)
     struct in_addr laddr;
 #endif /* COMMENT */
 
+    debug(F100,"getlocalipaddrs","",0);
     memset(&l_sa,0,slen);
     memset(&r_sa,0,slen);
 
@@ -6909,7 +7061,7 @@ getlocalipaddrs(buf,bufsz,index)
         /* resolve host name for local address */
         debug(F110,"getlocalipaddrs","calling gethostbyname()",0);
         host = gethostbyname(localhost);
-        debug(F111,"getlocalipaddrs","gethostbyname() returned",host);
+        /* debug(F111,"getlocalipaddrs","gethostbyname() returned",host); */
         if (host) {
 #ifdef HADDRLIST
             host = ck_copyhostent(host);
@@ -9793,6 +9945,10 @@ x25dump_prim(primitive)    N_npi_ctl_t *primitive; {
 #endif /* SYSUTIMEH */
 #endif /* OS2 */
 
+#ifdef VMS                             /* SMS 2007/02/15 */
+#include "ckvrtl.h"
+#endif /* def VMS */
+
 #ifndef HTTP_VERSION
 #define HTTP_VERSION "HTTP/1.1"
 #endif /* HTTP_VERSION */
@@ -10240,9 +10396,9 @@ http_open(hostname, svcname, use_ssl, rdns_name, rdns_len, agent)
 /* because INADDR_NONE should be all 1's anyway, thus the OR part is */
 /* probably superfluous -- not sure why it's even there, maybe it should be */
 /* removed. */
-        iax.s_addr == INADDR_NONE || iax.s_addr == (unsigned long) -1L
+        iax.s_addr == INADDR_NONE /* || iax.s_addr == (unsigned long) -1L */
 #else /* INADDR_NONE */
-        iax < 0
+        iax == -1
 #endif /* INADDR_NONE */
         ) {
         if (!quiet) {
@@ -10274,6 +10430,7 @@ http_open(hostname, svcname, use_ssl, rdns_name, rdns_len, agent)
 #else  /* HADDRLIST */
             bcopy(host->h_addr, (caddr_t)&r_addr.sin_addr, host->h_length);
 #endif /* HADDRLIST */
+#ifdef COMMENT
 #ifndef EXCELAN
             debug(F111,"BCOPY","host->h_addr",host->h_addr);
 #endif /* EXCELAN */
@@ -10281,6 +10438,7 @@ http_open(hostname, svcname, use_ssl, rdns_name, rdns_len, agent)
                   (caddr_t)&r_addr.sin_addr);
             debug(F111,"BCOPY"," r_addr.sin_addr.s_addr",
                   r_addr.sin_addr.s_addr);
+#endif /* COMMENT */
             debug(F111,"BCOPY","host->h_length",host->h_length);
         }
     }
@@ -10724,6 +10882,11 @@ http_close()
     int x = 0;
     debug(F101,"http_close","",httpfd);
 
+#ifdef HTTP_BUFFERING
+    http_count = 0;
+    http_bufp = 0;
+#endif /* HTTP_BUFFERING */
+
     if (httpfd == -1)                    /* Was open? */
       return(0);                        /* Wasn't. */
 
@@ -10772,7 +10935,7 @@ http_tol(s,n) CHAR *s; int n; {
     }
     debug(F101,"http_tol TCPIPLIB ttnet","",ttnet);
 #ifdef COMMENT
-    hexdump("http_tol",s,n);
+    ckhexdump("http_tol",s,n);
 #endif /* COMMENT */
 
 #ifdef CK_SSL
@@ -10943,12 +11106,15 @@ http_tol(s,n) CHAR *s; int n; {
     }
 }
 
-
 int
 http_inc(timo) int timo; {
     int x=-1; unsigned char c;             /* The locals. */
 
     if (httpfd == -1) {
+#ifdef HTTP_BUFFERING
+       http_count = 0;
+       http_bufp = 0;
+#endif /* HTTP_BUFFERING */
         debug(F100,"http_inc socket is closed","",0);
         return(-2);
     }
@@ -11066,6 +11232,13 @@ http_inc(timo) int timo; {
         }
     }
 #endif /* CK_SSL */
+
+#ifdef HTTP_BUFFERING
+    /* Skip all the select() stuff if we have bytes buffered locally */
+    if (http_count > 0)
+      goto getfrombuffer;
+#endif /* HTTP_BUFFERING */
+
     {
 #ifdef BSDSELECT
         fd_set rfds;
@@ -11096,6 +11269,10 @@ http_inc(timo) int timo; {
                 int s_errno = socket_errno;
                 debug(F111,"http_inc","select",rc);
                 debug(F111,"http_inc","socket_errno",s_errno);
+#ifdef HTTP_BUFFERING
+               http_count = 0;
+               http_bufp = 0;
+#endif /* HTTP_BUFFERING */
                 if (s_errno)
                     return(-1);
             }
@@ -11113,6 +11290,10 @@ http_inc(timo) int timo; {
                 if (!timo) {
 #ifdef TCPIPLIB
                     if ((rc = socket_write(httpfd,"",0)) < 0) {
+#ifdef HTTP_BUFFERING
+                       http_count = 0;
+                       http_bufp = 0;
+#endif /* HTTP_BUFFERING */
                         int s_errno = socket_errno;
                         debug(F101,"http_inc socket_write error","",s_errno);
 #ifdef OS2
@@ -11123,6 +11304,10 @@ http_inc(timo) int timo; {
                     }
 #else /* TCPIPLIB */
                     if ((rc = write(httpfd,"",0)) < 0) {
+#ifdef HTTP_BUFFERING
+                       http_count = 0;
+                       http_bufp = 0;
+#endif /* HTTP_BUFFERING */
                         debug(F101,"http_inc socket_write error","",errno);
                         return(-1); /* Call it an i/o error */
                     }
@@ -11158,6 +11343,10 @@ http_inc(timo) int timo; {
     }
 
     if (timo && x < 0) {        /* select() timed out */
+#ifdef HTTP_BUFFERING
+       http_count = 0;
+       http_bufp = 0;
+#endif /* HTTP_BUFFERING */
         debug(F100,"http_inc select() timed out","",0);
         return(-1); /* Call it an i/o error */
     }
@@ -11257,11 +11446,48 @@ http_inc(timo) int timo; {
             }
         }
 #endif /* CK_SSL */
+
+#ifdef HTTP_BUFFERING
+/*
+  Buffering code added by fdc 15 Dec 2005 for non-SSL case only because HTTP
+  GETs were orders of magnitude too slow due to the single-byte read()s.  The
+  file-descriptor swapping is pretty gross, but the more elegant solution
+  (calling a nettchk() like routine with the fd as a parameter) doesn't work,
+  because nettchk() relies on too many other routines that, like itself, are
+  hardwired for ttyfd.
+*/
+  getfrombuffer:
+       if (--http_count >= 0) {
+           c = http_inbuf[http_bufp++];
+           x = 1;
+       } else {
+           int savefd;
+           savefd = ttyfd;
+           ttyfd = httpfd;
+           x = nettchk();
+           ttyfd = savefd;             
+           debug(F101,"http_inc nettchk","",x);
+           if (x > HTTP_INBUFLEN)
+             x = HTTP_INBUFLEN;
+#ifdef TCPIPLIB
+           x = socket_read(httpfd,http_inbuf,x);
+#else  /* Not TCPIPLIB */
+           x = read(httpfd,http_inbuf,x);
+#endif /* TCPIPLIB */
+           http_count = 0;
+           http_bufp = 0;
+           if (x > 0) {
+               c = http_inbuf[http_bufp++];
+               http_count = x - 1;
+           }
+       }
+#else  /* Not HTTP_BUFFERING */
 #ifdef TCPIPLIB
         x = socket_read(httpfd,&c,1);
-#else
+#else  /* Not TCPIPLIB */
         x = read(httpfd,&c,1);
-#endif
+#endif /* TCPIPLIB */
+#endif /* HTTP_BUFFERING */
 
         if (x <= 0) {
             int s_errno = socket_errno;
@@ -11492,6 +11718,7 @@ http_get(agent, hdrlist, user, pwd, array, local, remote, stdio)
             } else if (!ckstrcmp(buf,"Transfer-Encoding:",18,0)) {
                 if ( ckindex("chunked",buf,18,0,0) != 0 )
                     chunked = 1;
+               debug(F101,"http_get chunked","",chunked);
             }
             i = 0;
         } else {
@@ -11955,6 +12182,7 @@ http_index(agent, hdrlist, user, pwd, array, local, remote, stdio)
                 } else if (!ckstrcmp(buf,"Transfer-Encoding:",18,0)) {
                     if ( ckindex("chunked",buf,18,0,0) != 0 )
                         chunked = 1;
+                   debug(F101,"http_index chunked","",chunked);
                 }
                 printf("%s\n",buf);
             }
@@ -12139,7 +12367,7 @@ http_put(agent, hdrlist, mime, user, pwd, array, local, remote, dest, stdio)
 #ifdef CMDATE2TM
     ckstrncat(request,http_now(),len);
 #else
-    strcat(request,...);
+    ckstrncat(request,...,len);
 #endif /* CMDATE2TM */
     ckstrncat(request,"\r\n",len);
     ckstrncat(request,"Host: ", len);
@@ -12259,6 +12487,7 @@ http_put(agent, hdrlist, mime, user, pwd, array, local, remote, dest, stdio)
                     } else if (!ckstrcmp(buf,"Transfer-Encoding:",18,0)) {
                         if ( ckindex("chunked",buf,18,0,0) != 0 )
                             chunked = 1;
+                       debug(F101,"http_put chunked","",chunked);
                     }
                     if ( stdio )
                         printf("%s\n",buf);
@@ -12432,7 +12661,7 @@ http_delete(agent, hdrlist, user, pwd, array, remote)
 #ifdef CMDATE2TM
     ckstrncat(request,http_now(),len);
 #else
-    strcat(request,...);
+    ckstrncat(request,...,len);
 #endif /* CMDATE2TM */
     ckstrncat(request,"\r\n",len);
     ckstrncat(request,"Host: ", len);
@@ -12515,6 +12744,7 @@ http_delete(agent, hdrlist, user, pwd, array, remote)
                 } else if (!ckstrcmp(buf,"Transfer-Encoding:",18,0)) {
                     if ( ckindex("chunked",buf,18,0,0) != 0 )
                         chunked = 1;
+                   debug(F101,"http_delete chunked","",chunked);
                 }
                 printf("%s\n",buf);
             }
@@ -12705,7 +12935,13 @@ http_post(agent, hdrlist, mime, user, pwd, array, local, remote, dest,
     sprintf(buf,"Content-length: %d\r\n",filelen); /* safe */
     ckstrncat(request,buf,len);
     ckstrncat(request,"\r\n",len);
+#ifdef COMMENT
+    /* This is apparently a mistake - the previous ckstrncat() already  */
+    /* appended a blank line to the request.  There should only be one. */
+    /* Servers are not required by RFC 2616 to ignore extraneous empty  */
+    /* lines.  -fdc, 28 Aug 2005. */
     ckstrncat(request,"\r\n",len);
+#endif /* COMMENT */
 
     /* Now we have the contents of the file */
   postopen:
@@ -12780,6 +13016,7 @@ http_post(agent, hdrlist, mime, user, pwd, array, local, remote, dest,
                     } else if (!ckstrcmp(buf,"Transfer-Encoding:",18,0)) {
                         if ( ckindex("chunked",buf,18,0,0) != 0 )
                             chunked = 1;
+                       debug(F101,"http_post chunked","",chunked);
                     }
                     if (stdio)
                         printf("%s\n",buf);
@@ -12899,7 +13136,6 @@ http_connect(socket, agent, hdrlist, user, pwd, array, host_port)
     char b64out[256];
     char * headers[HTTPHEADCNT];
     int    connected = 0;
-    int    chunked = 0;
 
     tcp_http_proxy_errno = 0;
 
@@ -13599,11 +13835,11 @@ fwdx_open_client_channel(channel) int channel; {
 
     env = getenv("DISPLAY");
     if ( !env )
-        env = tn_get_display();
+      env = (char *)tn_get_display();
     if ( env )
-        ckstrncpy(buf,env,256);
+      ckstrncpy(buf,env,256);
     else
-        ckstrncpy(buf,"127.0.0.1:0.0",256);
+      ckstrncpy(buf,"127.0.0.1:0.0",256);
 
     bzero((char *)&saddr,sizeof(saddr));
     saddr.sin_family = AF_INET;
@@ -13741,11 +13977,11 @@ fwdx_server_avail() {
 
     env = getenv("DISPLAY");
     if ( !env )
-        env = tn_get_display();
+      env = (char *)tn_get_display();
     if ( env )
-        ckstrncpy(buf,env,256);
+      ckstrncpy(buf,env,256);
     else
-        ckstrncpy(buf,"127.0.0.1:0.0",256);
+      ckstrncpy(buf,"127.0.0.1:0.0",256);
 
     bzero((char *)&saddr,sizeof(saddr));
     saddr.sin_family = AF_INET;
@@ -14071,7 +14307,7 @@ fwdx_write_data_to_channel(channel, data, len)
 
     sock = TELOPT_SB(TELOPT_FORWARD_X).forward_x.channel[i].fd;
     debug(F111,"fwdx_write_data_to_channel","socket",sock);
-    hexdump("fwdx_write_data_to_channel",data,len);
+    ckhexdump("fwdx_write_data_to_channel",data,len);
 
   fwdx_write_data_to_channel_retry: