|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T t
Length: 7346 (0x1cb2) Types: TextFile Names: »ts2tcp.c«
└─⟦2d1937cfd⟧ Bits:30007241 EUUGD22: P.P 5.0 └─⟦e83f91978⟧ »EurOpenD22/isode/osimis-2.0.tar.Z« └─⟦d846658bd⟧ └─⟦this⟧ »osimis/misode/tsap/ts2tcp.c« └─⟦2d1937cfd⟧ Bits:30007241 EUUGD22: P.P 5.0 └─⟦35176feda⟧ »EurOpenD22/isode/isode-6.tar.Z« └─⟦de7628f85⟧ └─⟦this⟧ »isode-6.0/tsap/ts2tcp.c«
/* ts2tcp.c - TPM: TCP interface */ #ifndef lint static char *rcsid = "$Header: /f/osi/tsap/RCS/ts2tcp.c,v 7.2 89/12/08 09:41:39 mrose Exp $"; #endif /* * $Header: /f/osi/tsap/RCS/ts2tcp.c,v 7.2 89/12/08 09:41:39 mrose Exp $ * * * $Log: ts2tcp.c,v $ * Revision 7.2 89/12/08 09:41:39 mrose * touch-up * * Revision 7.1 89/12/07 01:07:36 mrose * queued writes * * Revision 7.0 89/11/23 22:30:40 mrose * Release 6.0 * */ /* * NOTICE * * Acquisition, use, and distribution of this module and related * materials are subject to the restrictions of a license agreement. * Consult the Preface in the User's Manual for the full terms of * this agreement. * */ /* LINTLIBRARY */ #include <stdio.h> #include "tpkt.h" #include "tailor.h" #ifdef TCP #include "internet.h" #include <errno.h> #ifdef BSD42 #include <sys/ioctl.h> #endif #define MAX1006 2048 /* could be as high as TPKT_MAXLEN */ /* \f DATA */ #ifdef FIONBIO #define NODELAY #endif #ifdef NODELAY static fd_set inprogress; static struct sockaddr_in *peers = NULL; #endif extern int errno; /* \f N-CONNECT.REQUEST */ int tcpopen (tb, local, remote, td, async) register struct tsapblk *tb; struct NSAPaddr *local, *remote; struct TSAPdisconnect *td; int async; { int fd; #ifdef FIONBIO int onoff; #endif struct sockaddr_in lo_socket, in_socket; register struct sockaddr_in *lsock = &lo_socket, *isock = &in_socket; register struct hostent *hp; register struct servent *sp; #ifndef NODELAY if (async) return tsaplose (td, DR_PARAMETER, NULLCP, "asynchronous not supported"); #endif bzero ((char *) isock, sizeof *isock); if (remote -> na_port == 0) isock -> sin_port = (sp = getservbyname ("tsap", "tcp")) ? sp -> s_port : htons ((u_short) 102); else isock -> sin_port = remote -> na_port; if ((hp = gethostbystring (remote -> na_domain)) == NULL) return tsaplose (td, DR_ADDRESS, NULLCP, "%s: unknown host", remote -> na_domain); #ifdef notanymore (void) strncpy (remote -> na_domain, hp -> h_name, sizeof remote -> na_domain); #endif isock -> sin_family = hp -> h_addrtype; inaddr_copy (hp, isock); #ifndef notanymore (void) strcpy (remote -> na_domain, inet_ntoa (isock -> sin_addr)); #endif if (local && local -> na_domain[0]) { bzero ((char *) lsock, sizeof *lsock); if ((hp = gethostbystring (local -> na_domain)) == NULL) return tsaplose (td, DR_ADDRESS, NULLCP, "%s: unknown host", local -> na_domain); if ((lsock -> sin_family = hp -> h_addrtype) != isock -> sin_family) return tsaplose (td, DR_ADDRESS, NULLCP, "address family mismatch"); inaddr_copy (hp, lsock); } else lsock = NULL; if ((fd = start_tcp_client (lsock, 0)) == NOTOK) return tsaplose (td, DR_CONGEST, "socket", "unable to start"); #ifdef FIONBIO if (async) (void) ioctl (fd, FIONBIO, (onoff = 1, (char *) &onoff)); #endif tb -> tb_fd = fd; (void) TTService (tb); if (join_tcp_server (fd, isock) == NOTOK) { #ifdef NODELAY if (async) switch (errno) { case EINPROGRESS: if (peers == NULL) { peers = (struct sockaddr_in *) calloc ((unsigned) getdtablesize (), sizeof *peers); if (peers == NULL) { (void) tsaplose (td, DR_CONGEST, NULLCP, "out of memory"); (void) close_tcp_socket (fd); return (tb -> tb_fd = NOTOK); } FD_ZERO (&inprogress); } FD_SET (fd, &inprogress); peers[fd] = *isock;/* struct copy */ return OK; case EISCONN: goto done; default: break; } #endif (void) tsaplose (td, DR_REFUSED, "connection", "unable to establish"); (void) close_tcp_socket (fd); return (tb -> tb_fd = NOTOK); } #ifdef NODELAY done: ; #endif #ifdef FIONBIO if (async) (void) ioctl (fd, FIONBIO, (onoff = 0, (char *) &onoff)); #endif return DONE; } /* \f */ #ifndef NODELAY /* ARGSUSED */ #endif static int tcpretry (tb, td) struct tsapblk *tb; struct TSAPdisconnect *td; { #ifdef NODELAY #ifdef FIONBIO int onoff; #endif int fd = tb -> tb_fd; fd_set mask; struct sockaddr_in *isock = &peers[fd]; FD_ZERO (&mask); FD_SET (fd, &mask); if (xselect (fd + 1, NULLFD, &mask, NULLFD, 0) < 1) return OK; if (!FD_ISSET (fd, &inprogress)) return DONE; isock = &peers[fd]; if (join_tcp_server (fd, isock) == NOTOK) { switch (errno) { case EINPROGRESS: return OK; case EISCONN: goto done; case EINVAL: /* UNIX bug: could be any socket errno, e.g., ETIMEDOUT */ errno = ECONNREFUSED; /* and fall */ default: break; } (void) tsaplose (td, DR_REFUSED, "connection", "unable to establish"); FD_CLR (fd, &inprogress); (void) close_tcp_socket (fd); return (tb -> tb_fd = NOTOK); } done: ; #ifdef FIONBIO (void) ioctl (fd, FIONBIO, (onoff = 0, (char *) &onoff)); #endif FD_CLR (fd, &inprogress); return DONE; #else return tsaplose (td, DR_OPERATION, NULLCP, "connection not in progress"); #endif } /* \f init for read from network */ #ifndef BRIDGE_X25 static #endif int tcpinit (fd, t) int fd; register struct tsapkt *t; { register int cc, i; register char *bp; for (bp = (char *) &t -> t_pkthdr, i = TPKT_HDRLEN (t); i > 0; bp += cc, i -= cc) switch (cc = read_tcp_socket (fd, bp, i)) { case NOTOK: case OK: return DR_NETWORK; default: break; } if (t -> t_vrsn != TPKT_VRSN) return DR_PROTOCOL; if ((t -> t_length = ntohs (t -> t_length)) < TPKT_HDRLEN (t)) return DR_LENGTH; return OK; } /* \f */ /* ARGSUSED */ char *tcpsave (fd, sin, cp1, cp2, td) int fd; struct sockaddr_in *sin; char *cp1, *cp2; struct TSAPdisconnect *td; { static char buffer[BUFSIZ]; (void) sprintf (buffer, "%c%d %s %s", NT_TCP, fd, cp1, cp2); return buffer; } /* \f */ int tcprestore (tb, buffer, td) register struct tsapblk *tb; char *buffer; struct TSAPdisconnect *td; { int fd; char domain[NSAP_DOMAINLEN + 1]; register struct NSAPaddr *na; register struct TSAPaddr *ta; ta = &tb -> tb_initiating; ta -> ta_naddr = 1; na = ta -> ta_addrs; na -> na_type = NA_TCP; na -> na_subnet = ts_comm_tcp_default; if (sscanf (buffer, "%d %s %s", &fd, na -> na_domain, domain) != 3 || fd < 0) return tsaplose (td, DR_PARAMETER, NULLCP, "bad initialization vector \"%s\"", buffer); tb -> tb_fd = fd; (void) TTService (tb); ta = &tb -> tb_responding; ta -> ta_naddr = 1; na = ta -> ta_addrs; na -> na_type = NA_TCP; na -> na_subnet = ts_comm_tcp_default; (void) strncpy (na -> na_domain, domain, sizeof na -> na_domain); return OK; } /* \f */ int TTService (tb) register struct tsapblk *tb; { struct tsapkt *t; tb -> tb_flags |= TB_TCP; tb -> tb_tsdusize = MAX1006 - (tb -> tb_tpduslop = sizeof t -> t_pkthdr + DT_MAGIC); tb -> tb_retryfnx = tcpretry; tb -> tb_initfnx = tcpinit; tb -> tb_readfnx = read_tcp_socket; tb -> tb_writefnx = tp0write; tb -> tb_closefnx = close_tcp_socket; tb -> tb_selectfnx = select_tcp_socket; tp0init (tb); } #endif