aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorRichard M. Stallman1996-06-08 00:22:50 +0000
committerRichard M. Stallman1996-06-08 00:22:50 +0000
commitf249a012806470657c8c4c11e8390ea299b60597 (patch)
tree140a0edd59f2fd99a6caa9521e86ec2bad86f54a /src
parenta11e68d017e1dd8a8759c0f63fa601fd92eb5d66 (diff)
downloademacs-f249a012806470657c8c4c11e8390ea299b60597.tar.gz
emacs-f249a012806470657c8c4c11e8390ea299b60597.zip
(init_environment): Read PRELOAD_WINSOCK from registry if
not set in environment. (winsock_inuse) [HAVE_SOCKETS]: New variable. (have_winsock) [HAVE_SOCKETS]: Obsolete variable removed. (term_winsock) [HAVE_SOCKETS]: Only unload winsock library if there are no active sockets still open, and if the cleanup function succeeds. Return TRUE if winsock is unloaded. (init_winsock) [HAVE_SOCKETS]: Load winsock if not already loaded, and return TRUE if winsock support is available. Unload winsock immediately if new parameter load_now is false. Check that WSAStartup supports the winsock version we requested. (set_errno, check_errno, sys_socket, sys_bind, sys_connect, sys_htons, sys_ntohs, sys_inet_addr, sys_gethostname, sys_gethostbyname, sys_getservbyname, sys_close, sys_read, sys_write) [HAVE_SOCKETS]: Check winsock_lib instead of have_winsock to determine if winsock support is available. (sys_socket, sys_close) [HAVE_SOCKETS]: Count sockets in use. (init_ntproc) [HAVE_SOCKETS]: Only load winsock library on startup if PRELOAD_WINSOCK is set in environment (or registry).
Diffstat (limited to 'src')
-rw-r--r--src/w32.c102
1 files changed, 74 insertions, 28 deletions
diff --git a/src/w32.c b/src/w32.c
index adda8f0ee85..bd6fdd9a2da 100644
--- a/src/w32.c
+++ b/src/w32.c
@@ -584,6 +584,7 @@ init_environment ()
584 static char * env_vars[] = 584 static char * env_vars[] =
585 { 585 {
586 "HOME", 586 "HOME",
587 "PRELOAD_WINSOCK",
587 "emacs_dir", 588 "emacs_dir",
588 "EMACSLOADPATH", 589 "EMACSLOADPATH",
589 "SHELL", 590 "SHELL",
@@ -1389,25 +1390,35 @@ BOOL (WINAPI *pfn_SetHandleInformation) (HANDLE object, DWORD mask, DWORD flags)
1389#define HANDLE_FLAG_INHERIT 1 1390#define HANDLE_FLAG_INHERIT 1
1390#endif 1391#endif
1391 1392
1392static int have_winsock; 1393HANDLE winsock_lib;
1393static HANDLE winsock_lib; 1394static int winsock_inuse;
1394 1395
1395static void 1396BOOL
1396term_winsock (void) 1397term_winsock (void)
1397{ 1398{
1398 if (have_winsock) 1399 if (winsock_lib != NULL && winsock_inuse == 0)
1399 { 1400 {
1400 pfn_WSACleanup (); 1401 /* Not sure what would cause WSAENETDOWN, or even if it can happen
1401 FreeLibrary (winsock_lib); 1402 after WSAStartup returns successfully, but it seems reasonable
1403 to allow unloading winsock anyway in that case. */
1404 if (pfn_WSACleanup () == 0 ||
1405 pfn_WSAGetLastError () == WSAENETDOWN)
1406 {
1407 if (FreeLibrary (winsock_lib))
1408 winsock_lib = NULL;
1409 return TRUE;
1410 }
1402 } 1411 }
1412 return FALSE;
1403} 1413}
1404 1414
1405static void 1415BOOL
1406init_winsock () 1416init_winsock (int load_now)
1407{ 1417{
1408 WSADATA winsockData; 1418 WSADATA winsockData;
1409 1419
1410 have_winsock = FALSE; 1420 if (winsock_lib != NULL)
1421 return TRUE;
1411 1422
1412 pfn_SetHandleInformation = NULL; 1423 pfn_SetHandleInformation = NULL;
1413 pfn_SetHandleInformation 1424 pfn_SetHandleInformation
@@ -1443,16 +1454,36 @@ init_winsock ()
1443 LOAD_PROC( getservbyname ); 1454 LOAD_PROC( getservbyname );
1444 LOAD_PROC( WSACleanup ); 1455 LOAD_PROC( WSACleanup );
1445 1456
1457#undef LOAD_PROC
1458
1446 /* specify version 1.1 of winsock */ 1459 /* specify version 1.1 of winsock */
1447 if (pfn_WSAStartup (0x101, &winsockData) == 0) 1460 if (pfn_WSAStartup (0x101, &winsockData) == 0)
1448 { 1461 {
1449 have_winsock = TRUE; 1462 if (winsockData.wVersion != 0x101)
1450 return; 1463 goto fail;
1464
1465 if (!load_now)
1466 {
1467 /* Report that winsock exists and is usable, but leave
1468 socket functions disabled. I am assuming that calling
1469 WSAStartup does not require any network interaction,
1470 and in particular does not cause or require a dial-up
1471 connection to be established. */
1472
1473 pfn_WSACleanup ();
1474 FreeLibrary (winsock_lib);
1475 winsock_lib = NULL;
1476 }
1477 winsock_inuse = 0;
1478 return TRUE;
1451 } 1479 }
1452 1480
1453 fail: 1481 fail:
1454 FreeLibrary (winsock_lib); 1482 FreeLibrary (winsock_lib);
1483 winsock_lib = NULL;
1455 } 1484 }
1485
1486 return FALSE;
1456} 1487}
1457 1488
1458 1489
@@ -1463,7 +1494,7 @@ int h_errno = 0;
1463 are already in <sys/socket.h> */ 1494 are already in <sys/socket.h> */
1464static void set_errno () 1495static void set_errno ()
1465{ 1496{
1466 if (!have_winsock) 1497 if (winsock_lib == NULL)
1467 h_errno = EINVAL; 1498 h_errno = EINVAL;
1468 else 1499 else
1469 h_errno = pfn_WSAGetLastError (); 1500 h_errno = pfn_WSAGetLastError ();
@@ -1484,7 +1515,7 @@ static void set_errno ()
1484 1515
1485static void check_errno () 1516static void check_errno ()
1486{ 1517{
1487 if (h_errno == 0 && have_winsock) 1518 if (h_errno == 0 && winsock_lib != NULL)
1488 pfn_WSASetLastError (0); 1519 pfn_WSASetLastError (0);
1489} 1520}
1490 1521
@@ -1507,7 +1538,7 @@ sys_socket(int af, int type, int protocol)
1507 long s; 1538 long s;
1508 child_process * cp; 1539 child_process * cp;
1509 1540
1510 if (!have_winsock) 1541 if (winsock_lib == NULL)
1511 { 1542 {
1512 h_errno = ENETDOWN; 1543 h_errno = ENETDOWN;
1513 return INVALID_SOCKET; 1544 return INVALID_SOCKET;
@@ -1587,6 +1618,7 @@ sys_socket(int af, int type, int protocol)
1587 fd_info[ fd ].cp = cp; 1618 fd_info[ fd ].cp = cp;
1588 1619
1589 /* success! */ 1620 /* success! */
1621 winsock_inuse++; /* count open sockets */
1590 return fd; 1622 return fd;
1591 } 1623 }
1592 1624
@@ -1605,7 +1637,7 @@ sys_socket(int af, int type, int protocol)
1605int 1637int
1606sys_bind (int s, const struct sockaddr * addr, int namelen) 1638sys_bind (int s, const struct sockaddr * addr, int namelen)
1607{ 1639{
1608 if (!have_winsock) 1640 if (winsock_lib == NULL)
1609 { 1641 {
1610 h_errno = ENOTSOCK; 1642 h_errno = ENOTSOCK;
1611 return SOCKET_ERROR; 1643 return SOCKET_ERROR;
@@ -1627,7 +1659,7 @@ sys_bind (int s, const struct sockaddr * addr, int namelen)
1627int 1659int
1628sys_connect (int s, const struct sockaddr * name, int namelen) 1660sys_connect (int s, const struct sockaddr * name, int namelen)
1629{ 1661{
1630 if (!have_winsock) 1662 if (winsock_lib == NULL)
1631 { 1663 {
1632 h_errno = ENOTSOCK; 1664 h_errno = ENOTSOCK;
1633 return SOCKET_ERROR; 1665 return SOCKET_ERROR;
@@ -1648,28 +1680,28 @@ sys_connect (int s, const struct sockaddr * name, int namelen)
1648u_short 1680u_short
1649sys_htons (u_short hostshort) 1681sys_htons (u_short hostshort)
1650{ 1682{
1651 return (have_winsock) ? 1683 return (winsock_lib != NULL) ?
1652 pfn_htons (hostshort) : hostshort; 1684 pfn_htons (hostshort) : hostshort;
1653} 1685}
1654 1686
1655u_short 1687u_short
1656sys_ntohs (u_short netshort) 1688sys_ntohs (u_short netshort)
1657{ 1689{
1658 return (have_winsock) ? 1690 return (winsock_lib != NULL) ?
1659 pfn_ntohs (netshort) : netshort; 1691 pfn_ntohs (netshort) : netshort;
1660} 1692}
1661 1693
1662unsigned long 1694unsigned long
1663sys_inet_addr (const char * cp) 1695sys_inet_addr (const char * cp)
1664{ 1696{
1665 return (have_winsock) ? 1697 return (winsock_lib != NULL) ?
1666 pfn_inet_addr (cp) : INADDR_NONE; 1698 pfn_inet_addr (cp) : INADDR_NONE;
1667} 1699}
1668 1700
1669int 1701int
1670sys_gethostname (char * name, int namelen) 1702sys_gethostname (char * name, int namelen)
1671{ 1703{
1672 if (have_winsock) 1704 if (winsock_lib != NULL)
1673 return pfn_gethostname (name, namelen); 1705 return pfn_gethostname (name, namelen);
1674 1706
1675 if (namelen > MAX_COMPUTERNAME_LENGTH) 1707 if (namelen > MAX_COMPUTERNAME_LENGTH)
@@ -1684,7 +1716,7 @@ sys_gethostbyname(const char * name)
1684{ 1716{
1685 struct hostent * host; 1717 struct hostent * host;
1686 1718
1687 if (!have_winsock) 1719 if (winsock_lib == NULL)
1688 { 1720 {
1689 h_errno = ENETDOWN; 1721 h_errno = ENETDOWN;
1690 return NULL; 1722 return NULL;
@@ -1702,7 +1734,7 @@ sys_getservbyname(const char * name, const char * proto)
1702{ 1734{
1703 struct servent * serv; 1735 struct servent * serv;
1704 1736
1705 if (!have_winsock) 1737 if (winsock_lib == NULL)
1706 { 1738 {
1707 h_errno = ENETDOWN; 1739 h_errno = ENETDOWN;
1708 return NULL; 1740 return NULL;
@@ -1751,13 +1783,16 @@ sys_close (int fd)
1751 } 1783 }
1752 if (i == MAXDESC) 1784 if (i == MAXDESC)
1753 { 1785 {
1754#if defined (HAVE_SOCKETS) && !defined (SOCK_REPLACE_HANDLE) 1786#ifdef HAVE_SOCKETS
1755 if (fd_info[fd].flags & FILE_SOCKET) 1787 if (fd_info[fd].flags & FILE_SOCKET)
1756 { 1788 {
1757 if (!have_winsock) abort (); 1789#ifndef SOCK_REPLACE_HANDLE
1790 if (winsock_lib == NULL) abort ();
1758 1791
1759 pfn_shutdown (SOCK_HANDLE (fd), 2); 1792 pfn_shutdown (SOCK_HANDLE (fd), 2);
1760 rc = pfn_closesocket (SOCK_HANDLE (fd)); 1793 rc = pfn_closesocket (SOCK_HANDLE (fd));
1794#endif
1795 winsock_inuse--; /* count open sockets */
1761 } 1796 }
1762#endif 1797#endif
1763 delete_child (cp); 1798 delete_child (cp);
@@ -2010,7 +2045,7 @@ sys_read (int fd, char * buffer, unsigned int count)
2010#ifdef HAVE_SOCKETS 2045#ifdef HAVE_SOCKETS
2011 else /* FILE_SOCKET */ 2046 else /* FILE_SOCKET */
2012 { 2047 {
2013 if (!have_winsock) abort (); 2048 if (winsock_lib == NULL) abort ();
2014 2049
2015 /* do the equivalent of a non-blocking read */ 2050 /* do the equivalent of a non-blocking read */
2016 pfn_ioctlsocket (SOCK_HANDLE (fd), FIONREAD, &waiting); 2051 pfn_ioctlsocket (SOCK_HANDLE (fd), FIONREAD, &waiting);
@@ -2070,7 +2105,7 @@ sys_write (int fd, const void * buffer, unsigned int count)
2070#ifdef HAVE_SOCKETS 2105#ifdef HAVE_SOCKETS
2071 if (fd_info[fd].flags & FILE_SOCKET) 2106 if (fd_info[fd].flags & FILE_SOCKET)
2072 { 2107 {
2073 if (!have_winsock) abort (); 2108 if (winsock_lib == NULL) abort ();
2074 nchars = pfn_send (SOCK_HANDLE (fd), buffer, count, 0); 2109 nchars = pfn_send (SOCK_HANDLE (fd), buffer, count, 0);
2075 if (nchars == SOCKET_ERROR) 2110 if (nchars == SOCKET_ERROR)
2076 { 2111 {
@@ -2103,8 +2138,19 @@ void
2103init_ntproc () 2138init_ntproc ()
2104{ 2139{
2105#ifdef HAVE_SOCKETS 2140#ifdef HAVE_SOCKETS
2106 /* initialise the socket interface if available */ 2141 /* Initialise the socket interface now if available and requested by
2107 init_winsock (); 2142 the user by defining PRELOAD_WINSOCK; otherwise loading will be
2143 delayed until open-network-stream is called (win32-has-winsock can
2144 also be used to dynamically load or reload winsock).
2145
2146 Conveniently, init_environment is called before us, so
2147 PRELOAD_WINSOCK can be set in the registry. */
2148
2149 /* Always initialize this correctly. */
2150 winsock_lib = NULL;
2151
2152 if (getenv ("PRELOAD_WINSOCK") != NULL)
2153 init_winsock (TRUE);
2108#endif 2154#endif
2109 2155
2110 /* Initial preparation for subprocess support: replace our standard 2156 /* Initial preparation for subprocess support: replace our standard