home *** CD-ROM | disk | FTP | other *** search
- /*
- * tcp_util.c
- *
- *
- * by Eric Brown
- * 27 October '92
- */
- #include <windows.h>
- #include <stdio.h>
- #include <string.h>
- #include <stdlib.h>
- #include <winsock.h>
- #include <time.h>
-
- #include "lp.h"
-
- char *lp_printcap_server_lookup(char *printer)
- {
- return NULL;
- } /* lp_printcap_server_lookup() */
-
- int lp_tcp_startup()
- {
- WSADATA WSAData;
- return WSAStartup(0x0001, &WSAData);
- } /* lp_tcp_startup() */
-
- void lp_tcp_shutdown()
- {
- } /* lp_tcp_shutdown() */
-
-
- /*
- * NOTES:
- * This code is modified from _UNIX_NETWORK_PROGRAMMING_ by W. Richard Stevens,
- * pp. 398-399.
- */
- int lp_tcp_open(char *host)
- {
- struct sockaddr_in tcp_srv_addr;
- struct sockaddr_in tcp_my_addr;
- struct hostent tcp_host_info, *hp;
- unsigned long inaddr;
- int fd;
- int retries;
- int b_nolinger;
- struct linger linger;
-
- memset((void *)&tcp_srv_addr, 0, sizeof(tcp_srv_addr));
- tcp_srv_addr.sin_family =AF_INET;
- tcp_srv_addr.sin_port = htons((short)PRINTER_PORT);
-
- /*
- * First try to convert the host name as a dotted-decimal number.
- * Only if that fails do we call gethostbyname()
- */
- if ((inaddr = inet_addr(host)) != INADDR_NONE) {
- memcpy((void *)&tcp_srv_addr.sin_addr, (const void *)&inaddr,
- sizeof(inaddr));
- tcp_host_info.h_name = NULL;
- }
- else
- {
- if ((hp = gethostbyname(host)) == NULL) {
- fprintf(stderr, "tcp_open: hst name error: %s\n", host);
- return -1;
- } /* if */
- tcp_host_info = *hp;
- memcpy((void *)&tcp_srv_addr.sin_addr, (const void *)hp->h_addr,
- hp->h_length);
- } /* else */
-
-
- /*
- * Create an internet domain socket
- */
- if ((fd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
- fprintf(stderr, "tcp_open: can't get a reserved TCP port\n");
- return -1;
- } /* if */
-
-
- /*
- * Bind to a privledged port
- */
- memset((void *)&tcp_my_addr, 0, sizeof(tcp_my_addr));
- tcp_my_addr.sin_family = AF_INET;
- lp_randomize();
- retries = BIND_RETRIES;
- while((tcp_my_addr.sin_port = htons((short)(rand() % MAX_PRIV_PORT)),
- bind(fd, (struct sockaddr *)&tcp_my_addr, sizeof(struct sockaddr)))) {
- if (WSAGetLastError() == WSAEADDRINUSE && retries-- > 0)
- continue; /* Try again */
- else {
- fprintf(stderr, "tcp_open: Couldn't bind.\n");
- closesocket(fd);
- return -1;
- } /* else */
- } /* while */
- if (retries == 0) {
- fprintf(stderr, "tcp_open: Tried %d ports, couldn't bind to any.\n",
- BIND_RETRIES);
- closesocket(fd);
- return -1;
- } /* if */
-
-
- /*
- * Connect to the server
- */
- if (connect(fd, (struct sockaddr *)&tcp_srv_addr, sizeof(struct sockaddr)) < 0) {
- fprintf(stderr, "tcp_open: can't connect to server\n");
- closesocket(fd);
- return -1;
- } /* if */
-
-
- /*
- * Let us linger for 1 AND ONLY 1 second!
- * Without this bit of code, I found that doing an lpq or lprm
- * immediately after an lpr would frequently fail! -Eric.
- */
- b_nolinger = (int)FALSE; /* turn off DONTLINGER = turn on LINGER */
- linger.l_onoff = 1;
- linger.l_linger = 1; /* 1 second */
- setsockopt(fd, SOL_SOCKET, SO_DONTLINGER, (char *)&b_nolinger, sizeof(b_nolinger));
- setsockopt(fd, SOL_SOCKET, SO_LINGER, (char *)&linger, sizeof(linger));
-
-
- return(fd);
- } /* tcp_open() */
-
-
- void lp_randomize()
- {
- srand((unsigned)time(NULL));
- } /* lp_randomize() */
-
-