/* ckotcp.c * * TCP/IP interface DLL between C-Kermit and IBM TCP/IP * * Author: Kai-Uwe Rommel * Created: Wed May 25 1994 */ #include #include #include #ifdef __IBMC__ #define off_t _dummy_off_t /* avoid warning */ #include #undef off_t #else #define far _far #define cdecl _cdecl #include #endif #ifdef __TYPES_32H #define FDPTR /* TCP/IP 2.0 */ #define PACKED #else #define FDPTR (short * _Seg16) /* TCP/IP 1.2.1 */ #define PACKED _Packed #endif #include #include #include #include #define BSD_SELECT #include #include #define CK_DLL #include "ckotcp.h" int ENTRY ck_sockinit(void) { return sock_init(); } /* socket calls */ int ENTRY ck_connect(int socket, struct ck_sockaddr *name, int namelen) { struct sockaddr_in addr; memset(&addr, 0, sizeof(addr)); addr.sin_port = ((struct ck_sockaddr_in *) name) -> sin_port; addr.sin_family = ((struct ck_sockaddr_in *) name) -> sin_family; addr.sin_addr.s_addr = ((struct ck_sockaddr_in *) name) -> sin_addr.s_addr; return connect(socket, (struct sockaddr *) &addr, sizeof(addr)); } int ENTRY ck_ioctl(int socket, int cmd, char *data, int length) { switch (cmd) { case CK_FIONREAD: cmd = FIONREAD; break; case CK_FIONBIO: cmd = FIONBIO; break; default: return -1; } return ioctl(socket, cmd, data, length); } int ENTRY ck_recv(int socket, char *buffer, int length, int flags) { if (flags != 0) return -1; return recv(socket, buffer, length, flags); } int ENTRY ck_select(int *fds, int read, int write, int except, long timeout) { /* Warning: if the called select is 16-bit but the calling code is * 32-bit, only one fd can be pointed to by fds! However, calling * with one "read" socket is the only use of select() in * C-Kermit. Might change in the future, so this must be checked. */ #ifdef BSD_SELECT fd_set rfds; struct timeval tv; int socket = *fds; #endif if (read != 1 && write != 0 && except != 0) return -1; #ifdef BSD_SELECT FD_ZERO(&rfds); FD_SET(socket, &rfds); tv.tv_sec = tv.tv_usec = 0L; if (timeout < 1000) tv.tv_usec = (long) timeout * 1000L; else tv.tv_sec = timeout; return select(FD_SETSIZE, &rfds, NULL, NULL, &tv) && FD_ISSET(socket, &rfds); #else return select(FDPTR fds, read, write, except, timeout); #endif } int ENTRY ck_send(int socket, char *buffer, int length, int flags) { if (flags != 0) return -1; return send(socket, buffer, length, flags); } int ENTRY ck_setsockopt(int socket, int level, int optname, char *optvalue, int optlength) { if (level == CK_SOL_SOCKET) level = SOL_SOCKET; else return -1; if (optname == CK_SO_OOBINLINE) optname = SO_OOBINLINE; else return -1; return setsockopt(socket, level, optname, optvalue, optlength); } int ENTRY ck_socket(int domain, int type, int protocol) { if (domain == CK_AF_INET) domain = AF_INET; else return -1; if (type == CK_SOCK_STREAM) type = SOCK_STREAM; else return -1; if (protocol != 0) return -1; return socket(domain, type, protocol); } int ENTRY ck_soclose(int socket) { return soclose(socket); } /* utility calls */ struct ck_hostent * ENTRY ck_gethostbyname(char *name) { struct hostent *host = gethostbyname(name); static struct ck_hostent ckhost; if (host == NULL) return NULL; ckhost.h_name = host -> h_name; ckhost.h_aliases = NULL; ckhost.h_addrtype = host -> h_addrtype; ckhost.h_length = host -> h_length; ckhost.h_address = host -> h_addr; return &ckhost; } struct ck_servent * ENTRY ck_getservbyname(char *name, char *protocol) { PACKED struct servent *serv = getservbyname(name, protocol); static struct ck_servent ckserv; if (serv == NULL) return NULL; ckserv.s_name = serv -> s_name; ckserv.s_aliases = NULL; ckserv.s_port = serv -> s_port; ckserv.s_proto = serv -> s_proto; return &ckserv; } unsigned long ENTRY ck_inet_addr(char *cp) { return inet_addr(cp); } char * ENTRY ck_inet_ntoa(struct ck_in_addr in) { struct in_addr addr; addr.s_addr = in.s_addr; return inet_ntoa(addr); } /* end of ckotcp.c */