diff options
author | Corinna Vinschen <corinna@vinschen.de> | 2000-10-27 09:50:33 +0000 |
---|---|---|
committer | Corinna Vinschen <corinna@vinschen.de> | 2000-10-27 09:50:33 +0000 |
commit | afd5033d83e5871f96c15cd72d790692f643c4bd (patch) | |
tree | 5f00f39b22e5bd2d375aae794b94ef248f94b044 /winsup/cygwin/net.cc | |
parent | dd4f0b2343d5b25894824635281fe88d85281824 (diff) | |
download | cygnal-afd5033d83e5871f96c15cd72d790692f643c4bd.tar.gz cygnal-afd5033d83e5871f96c15cd72d790692f643c4bd.tar.bz2 cygnal-afd5033d83e5871f96c15cd72d790692f643c4bd.zip |
* fhandler_socket.cc: New file.
* Makefile.in: Add fhandler_socket.o to dependencies.
* fhandler.h: Change comment.
* net.cc Move all fhandler_socket methods to fhandler_socket.cc.
* winsup.h: Add declaration for `ws2_32_handle'.
Diffstat (limited to 'winsup/cygwin/net.cc')
-rw-r--r-- | winsup/cygwin/net.cc | 299 |
1 files changed, 2 insertions, 297 deletions
diff --git a/winsup/cygwin/net.cc b/winsup/cygwin/net.cc index 7f587a1de..50c097d74 100644 --- a/winsup/cygwin/net.cc +++ b/winsup/cygwin/net.cc @@ -44,8 +44,7 @@ int __stdcall rresvport (int *); int sscanf (const char *, const char *, ...); } /* End of "C" section */ -extern HANDLE ws2_32_handle; -WSADATA wsadata; +static WSADATA wsadata; /* Cygwin internal */ static SOCKET __stdcall @@ -1514,7 +1513,7 @@ out: ifc->ifc_len = cnt * sizeof (struct ifreq); } -static int +int get_ifconf (struct ifconf *ifc, int what) { unsigned long lip, lnp; @@ -1783,300 +1782,6 @@ endhostent (void) { } -/**********************************************************************/ -/* fhandler_socket */ - -fhandler_socket::fhandler_socket (const char *name) : - fhandler_base (FH_SOCKET, name) -{ - set_cb (sizeof *this); - set_need_fork_fixup (); - prot_info_ptr = (LPWSAPROTOCOL_INFOA) cmalloc (HEAP_BUF, - sizeof (WSAPROTOCOL_INFOA)); -} - -fhandler_socket::~fhandler_socket () -{ - if (prot_info_ptr) - cfree (prot_info_ptr); -} - -void -fhandler_socket::fixup_before_fork_exec (DWORD win_proc_id) -{ - int ret = 1; - - if (prot_info_ptr && - (ret = WSADuplicateSocketA (get_socket (), win_proc_id, prot_info_ptr))) - { - debug_printf ("WSADuplicateSocket error"); - set_winsock_errno (); - } - if (!ret && ws2_32_handle) - { - debug_printf ("WSADuplicateSocket went fine, dwServiceFlags1=%d", - prot_info_ptr->dwServiceFlags1); - } - else - { - fhandler_base::fixup_before_fork_exec (win_proc_id); - debug_printf ("Without Winsock 2.0"); - } -} - -void -fhandler_socket::fixup_after_fork (HANDLE parent) -{ - SOCKET new_sock = INVALID_SOCKET; - - debug_printf ("WSASocket begin, dwServiceFlags1=%d", - prot_info_ptr->dwServiceFlags1); - if (prot_info_ptr && - (new_sock = WSASocketA (FROM_PROTOCOL_INFO, - FROM_PROTOCOL_INFO, - FROM_PROTOCOL_INFO, - prot_info_ptr, 0, 0)) == INVALID_SOCKET) - { - debug_printf ("WSASocket error"); - set_winsock_errno (); - } - if (new_sock != INVALID_SOCKET && ws2_32_handle) - { - debug_printf ("WSASocket went fine"); - set_io_handle ((HANDLE) new_sock); - } - else - { - fhandler_base::fixup_after_fork (parent); - debug_printf ("Without Winsock 2.0"); - } -} - -int -fhandler_socket::dup (fhandler_base *child) -{ - fhandler_socket *fhs = (fhandler_socket *) child; - fhs->set_io_handle (get_io_handle ()); - fhs->fixup_before_fork_exec (GetCurrentProcessId ()); - if (ws2_32_handle) - { - fhs->fixup_after_fork (hMainProc); - return 0; - } - return fhandler_base::dup (child); -} - -int -fhandler_socket::read (void *ptr, size_t len) -{ - sigframe thisframe (mainthread); - int res = recv (get_socket (), (char *) ptr, len, 0); - if (res == SOCKET_ERROR) - { - set_winsock_errno (); - } - return res; -} - -int -fhandler_socket::write (const void *ptr, size_t len) -{ - sigframe thisframe (mainthread); - int res = send (get_socket (), (const char *) ptr, len, 0); - if (res == SOCKET_ERROR) - { - set_winsock_errno (); - if (get_errno () == ECONNABORTED || get_errno () == ECONNRESET) - _raise (SIGPIPE); - } - return res; -} - -/* Cygwin internal */ -int -fhandler_socket::close () -{ - int res = 0; - sigframe thisframe (mainthread); - - if (closesocket (get_socket ())) - { - set_winsock_errno (); - res = -1; - } - - return res; -} - -/* Cygwin internal */ -/* - * Return the flags settings for an interface. - */ -static int -get_if_flags (struct ifreq *ifr) -{ - struct sockaddr_in *sa = (struct sockaddr_in *) &ifr->ifr_addr; - - short flags = IFF_NOTRAILERS | IFF_UP | IFF_RUNNING; - if (sa->sin_addr.s_addr == INADDR_LOOPBACK) - flags |= IFF_LOOPBACK; - else - flags |= IFF_BROADCAST; - - ifr->ifr_flags = flags; - return 0; -} - -#define ASYNC_MASK (FD_READ|FD_WRITE|FD_OOB|FD_ACCEPT|FD_CONNECT) - -/* Cygwin internal */ -int -fhandler_socket::ioctl (unsigned int cmd, void *p) -{ - int res; - struct ifconf *ifc; - struct ifreq *ifr; - sigframe thisframe (mainthread); - - switch (cmd) - { - case SIOCGIFCONF: - ifc = (struct ifconf *) p; - if (ifc == 0) - { - set_errno (EINVAL); - return -1; - } - res = get_ifconf (ifc, cmd); - if (res) - debug_printf ("error in get_ifconf\n"); - break; - case SIOCGIFFLAGS: - ifr = (struct ifreq *) p; - if (ifr == 0) - { - set_errno (EINVAL); - return -1; - } - res = get_if_flags (ifr); - break; - case SIOCGIFBRDADDR: - case SIOCGIFNETMASK: - case SIOCGIFADDR: - { - char buf[2048]; - struct ifconf ifc; - ifc.ifc_len = sizeof (buf); - ifc.ifc_buf = buf; - struct ifreq *ifrp; - - struct ifreq *ifr = (struct ifreq *) p; - if (ifr == 0) - { - debug_printf ("ifr == NULL\n"); - set_errno (EINVAL); - return -1; - } - - res = get_ifconf (&ifc, cmd); - if (res) - { - debug_printf ("error in get_ifconf\n"); - break; - } - - debug_printf (" name: %s\n", ifr->ifr_name); - for (ifrp = ifc.ifc_req; - (caddr_t) ifrp < ifc.ifc_buf + ifc.ifc_len; - ++ifrp) - { - debug_printf ("testname: %s\n", ifrp->ifr_name); - if (! strcmp (ifrp->ifr_name, ifr->ifr_name)) - { - switch (cmd) - { - case SIOCGIFADDR: - ifr->ifr_addr = ifrp->ifr_addr; - break; - case SIOCGIFBRDADDR: - ifr->ifr_broadaddr = ifrp->ifr_broadaddr; - break; - case SIOCGIFNETMASK: - ifr->ifr_netmask = ifrp->ifr_netmask; - break; - } - break; - } - } - if ((caddr_t) ifrp >= ifc.ifc_buf + ifc.ifc_len) - { - set_errno (EINVAL); - return -1; - } - break; - } - case FIOASYNC: - res = WSAAsyncSelect (get_socket (), gethwnd (), WM_ASYNCIO, - *(int *) p ? ASYNC_MASK : 0); - syscall_printf ("Async I/O on socket %s", - *(int *) p ? "started" : "cancelled"); - set_async (*(int *) p); - break; - default: - /* We must cancel WSAAsyncSelect (if any) before setting socket to - * blocking mode - */ - if (cmd == FIONBIO && *(int *) p == 0) - WSAAsyncSelect (get_socket (), gethwnd (), 0, 0); - res = ioctlsocket (get_socket (), cmd, (unsigned long *) p); - if (res == SOCKET_ERROR) - set_winsock_errno (); - if (cmd == FIONBIO) - { - syscall_printf ("socket is now %sblocking", - *(int *) p ? "un" : ""); - /* Start AsyncSelect if async socket unblocked */ - if (*(int *) p && get_async ()) - WSAAsyncSelect (get_socket (), gethwnd (), WM_ASYNCIO, ASYNC_MASK); - } - break; - } - syscall_printf ("%d = ioctl_socket (%x, %x)", res, cmd, p); - return res; -} - -int -fhandler_socket::fcntl (int cmd, void *arg) -{ - int res = 0; - int request, current; - - switch (cmd) - { - case F_SETFL: - { - /* Care for the old O_NDELAY flag. If one of the flags is set, - both flags are set. */ - int new_flags = (int) arg; - if (new_flags & (O_NONBLOCK | OLD_O_NDELAY)) - new_flags |= O_NONBLOCK | OLD_O_NDELAY; - request = (new_flags & O_NONBLOCK) ? 1 : 0; - current = (get_flags () & O_NONBLOCK) ? 1 : 0; - if (request != current && (res = ioctl (FIONBIO, &request))) - break; - if (request) - set_flags (get_flags () | O_NONBLOCK | OLD_O_NDELAY); - else - set_flags (get_flags () & ~(O_NONBLOCK | OLD_O_NDELAY)); - break; - } - default: - res = fhandler_base::fcntl (cmd, arg); - break; - } - return res; -} - static void wsock_init () { |