1 /*
2 * Windows networking abstraction.
3 *
4 * For the IPv6 code in here I am indebted to Jeroen Massar and
5 * unfix.org.
6 */
7
8 #include <winsock2.h> /* need to put this first, for winelib builds */
9
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <assert.h>
13
14 #define NEED_DECLARATION_OF_SELECT /* in order to initialise it */
15
16 #include "putty.h"
17 #include "network.h"
18 #include "tree234.h"
19 #include "ssh.h"
20
21 #include <ws2tcpip.h>
22
23 #ifndef NO_IPV6
24 #ifdef __clang__
25 #pragma clang diagnostic push
26 #pragma clang diagnostic ignored "-Wmissing-braces"
27 #endif
28 const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT;
29 const struct in6_addr in6addr_loopback = IN6ADDR_LOOPBACK_INIT;
30 #ifdef __clang__
31 #pragma clang diagnostic pop
32 #endif
33 #endif
34
35 #define ipv4_is_loopback(addr) \
36 ((p_ntohl(addr.s_addr) & 0xFF000000L) == 0x7F000000L)
37
38 /*
39 * Mutable state that goes with a SockAddr: stores information
40 * about where in the list of candidate IP(v*) addresses we've
41 * currently got to.
42 */
43 typedef struct SockAddrStep_tag SockAddrStep;
44 struct SockAddrStep_tag {
45 #ifndef NO_IPV6
46 struct addrinfo *ai; /* steps along addr->ais */
47 #endif
48 int curraddr;
49 };
50
51 typedef struct NetSocket NetSocket;
52 struct NetSocket {
53 const char *error;
54 SOCKET s;
55 Plug *plug;
56 bufchain output_data;
57 bool connected;
58 bool writable;
59 bool frozen; /* this causes readability notifications to be ignored */
60 bool frozen_readable; /* this means we missed at least one readability
61 * notification while we were frozen */
62 bool localhost_only; /* for listening sockets */
63 char oobdata[1];
64 size_t sending_oob;
65 bool oobinline, nodelay, keepalive, privport;
66 enum { EOF_NO, EOF_PENDING, EOF_SENT } outgoingeof;
67 SockAddr *addr;
68 SockAddrStep step;
69 int port;
70 int pending_error; /* in case send() returns error */
71 /*
72 * We sometimes need pairs of Socket structures to be linked:
73 * if we are listening on the same IPv6 and v4 port, for
74 * example. So here we define `parent' and `child' pointers to
75 * track this link.
76 */
77 NetSocket *parent, *child;
78
79 Socket sock;
80 };
81
82 struct SockAddr {
83 int refcount;
84 char *error;
85 bool resolved;
86 bool namedpipe; /* indicates that this SockAddr is phony, holding a Windows
87 * named pipe pathname instead of a network address */
88 #ifndef NO_IPV6
89 struct addrinfo *ais; /* Addresses IPv6 style. */
90 #endif
91 unsigned long *addresses; /* Addresses IPv4 style. */
92 int naddresses;
93 char hostname[512]; /* Store an unresolved host name. */
94 };
95
96 /*
97 * Which address family this address belongs to. AF_INET for IPv4;
98 * AF_INET6 for IPv6; AF_UNSPEC indicates that name resolution has
99 * not been done and a simple host name is held in this SockAddr
100 * structure.
101 */
102 #ifndef NO_IPV6
103 #define SOCKADDR_FAMILY(addr, step) \
104 (!(addr)->resolved ? AF_UNSPEC : \
105 (step).ai ? (step).ai->ai_family : AF_INET)
106 #else
107 #define SOCKADDR_FAMILY(addr, step) \
108 (!(addr)->resolved ? AF_UNSPEC : AF_INET)
109 #endif
110
111 /*
112 * Start a SockAddrStep structure to step through multiple
113 * addresses.
114 */
115 #ifndef NO_IPV6
116 #define START_STEP(addr, step) \
117 ((step).ai = (addr)->ais, (step).curraddr = 0)
118 #else
119 #define START_STEP(addr, step) \
120 ((step).curraddr = 0)
121 #endif
122
123 static tree234 *sktree;
124
cmpfortree(void * av,void * bv)125 static int cmpfortree(void *av, void *bv)
126 {
127 NetSocket *a = (NetSocket *)av, *b = (NetSocket *)bv;
128 uintptr_t as = (uintptr_t) a->s, bs = (uintptr_t) b->s;
129 if (as < bs)
130 return -1;
131 if (as > bs)
132 return +1;
133 if (a < b)
134 return -1;
135 if (a > b)
136 return +1;
137 return 0;
138 }
139
cmpforsearch(void * av,void * bv)140 static int cmpforsearch(void *av, void *bv)
141 {
142 NetSocket *b = (NetSocket *)bv;
143 uintptr_t as = (uintptr_t) av, bs = (uintptr_t) b->s;
144 if (as < bs)
145 return -1;
146 if (as > bs)
147 return +1;
148 return 0;
149 }
150
151 DECL_WINDOWS_FUNCTION(static, int, WSAStartup, (WORD, LPWSADATA));
152 DECL_WINDOWS_FUNCTION(static, int, WSACleanup, (void));
153 DECL_WINDOWS_FUNCTION(static, int, closesocket, (SOCKET));
154 DECL_WINDOWS_FUNCTION(static, u_long, ntohl, (u_long));
155 DECL_WINDOWS_FUNCTION(static, u_long, htonl, (u_long));
156 DECL_WINDOWS_FUNCTION(static, u_short, htons, (u_short));
157 DECL_WINDOWS_FUNCTION(static, u_short, ntohs, (u_short));
158 DECL_WINDOWS_FUNCTION(static, int, gethostname, (char *, int));
159 DECL_WINDOWS_FUNCTION(static, struct hostent FAR *, gethostbyname,
160 (const char FAR *));
161 DECL_WINDOWS_FUNCTION(static, struct servent FAR *, getservbyname,
162 (const char FAR *, const char FAR *));
163 DECL_WINDOWS_FUNCTION(static, unsigned long, inet_addr, (const char FAR *));
164 DECL_WINDOWS_FUNCTION(static, char FAR *, inet_ntoa, (struct in_addr));
165 DECL_WINDOWS_FUNCTION(static, const char FAR *, inet_ntop,
166 (int, void FAR *, char *, size_t));
167 DECL_WINDOWS_FUNCTION(static, int, connect,
168 (SOCKET, const struct sockaddr FAR *, int));
169 DECL_WINDOWS_FUNCTION(static, int, bind,
170 (SOCKET, const struct sockaddr FAR *, int));
171 DECL_WINDOWS_FUNCTION(static, int, setsockopt,
172 (SOCKET, int, int, const char FAR *, int));
173 DECL_WINDOWS_FUNCTION(static, SOCKET, socket, (int, int, int));
174 DECL_WINDOWS_FUNCTION(static, int, listen, (SOCKET, int));
175 DECL_WINDOWS_FUNCTION(static, int, send, (SOCKET, const char FAR *, int, int));
176 DECL_WINDOWS_FUNCTION(static, int, shutdown, (SOCKET, int));
177 DECL_WINDOWS_FUNCTION(static, int, ioctlsocket,
178 (SOCKET, long, u_long FAR *));
179 DECL_WINDOWS_FUNCTION(static, SOCKET, accept,
180 (SOCKET, struct sockaddr FAR *, int FAR *));
181 DECL_WINDOWS_FUNCTION(static, int, getpeername,
182 (SOCKET, struct sockaddr FAR *, int FAR *));
183 DECL_WINDOWS_FUNCTION(static, int, recv, (SOCKET, char FAR *, int, int));
184 DECL_WINDOWS_FUNCTION(static, int, WSAIoctl,
185 (SOCKET, DWORD, LPVOID, DWORD, LPVOID, DWORD,
186 LPDWORD, LPWSAOVERLAPPED,
187 LPWSAOVERLAPPED_COMPLETION_ROUTINE));
188 #ifndef NO_IPV6
189 DECL_WINDOWS_FUNCTION(static, int, getaddrinfo,
190 (const char *nodename, const char *servname,
191 const struct addrinfo *hints, struct addrinfo **res));
192 DECL_WINDOWS_FUNCTION(static, void, freeaddrinfo, (struct addrinfo *res));
193 DECL_WINDOWS_FUNCTION(static, int, getnameinfo,
194 (const struct sockaddr FAR * sa, socklen_t salen,
195 char FAR * host, DWORD hostlen, char FAR * serv,
196 DWORD servlen, int flags));
197 DECL_WINDOWS_FUNCTION(static, char *, gai_strerror, (int ecode));
198 DECL_WINDOWS_FUNCTION(static, int, WSAAddressToStringA,
199 (LPSOCKADDR, DWORD, LPWSAPROTOCOL_INFO,
200 LPSTR, LPDWORD));
201 #endif
202
203 static HMODULE winsock_module = NULL;
204 static WSADATA wsadata;
205 #ifndef NO_IPV6
206 static HMODULE winsock2_module = NULL;
207 static HMODULE wship6_module = NULL;
208 #endif
209
sk_startup(int hi,int lo)210 static bool sk_startup(int hi, int lo)
211 {
212 WORD winsock_ver;
213
214 winsock_ver = MAKEWORD(hi, lo);
215
216 if (p_WSAStartup(winsock_ver, &wsadata)) {
217 return false;
218 }
219
220 if (LOBYTE(wsadata.wVersion) != LOBYTE(winsock_ver)) {
221 return false;
222 }
223
224 return true;
225 }
226
227 DEF_WINDOWS_FUNCTION(WSAAsyncSelect);
228 DEF_WINDOWS_FUNCTION(WSAEventSelect);
229 DEF_WINDOWS_FUNCTION(WSAGetLastError);
230 DEF_WINDOWS_FUNCTION(WSAEnumNetworkEvents);
231 DEF_WINDOWS_FUNCTION(select);
232
sk_init(void)233 void sk_init(void)
234 {
235 #ifndef NO_IPV6
236 winsock2_module =
237 #endif
238 winsock_module = load_system32_dll("ws2_32.dll");
239 if (!winsock_module) {
240 winsock_module = load_system32_dll("wsock32.dll");
241 }
242 if (!winsock_module)
243 modalfatalbox("Unable to load any WinSock library");
244
245 #ifndef NO_IPV6
246 /* Check if we have getaddrinfo in Winsock */
247 if (GetProcAddress(winsock_module, "getaddrinfo") != NULL) {
248 GET_WINDOWS_FUNCTION(winsock_module, getaddrinfo);
249 GET_WINDOWS_FUNCTION(winsock_module, freeaddrinfo);
250 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, getnameinfo);
251 /* This function would fail its type-check if we did one,
252 * because the VS header file provides an inline definition
253 * which is __cdecl instead of WINAPI. */
254 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, gai_strerror);
255 } else {
256 /* Fall back to wship6.dll for Windows 2000 */
257 wship6_module = load_system32_dll("wship6.dll");
258 if (wship6_module) {
259 GET_WINDOWS_FUNCTION(wship6_module, getaddrinfo);
260 GET_WINDOWS_FUNCTION(wship6_module, freeaddrinfo);
261 /* See comment above about type check */
262 GET_WINDOWS_FUNCTION_NO_TYPECHECK(wship6_module, getnameinfo);
263 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, gai_strerror);
264 } else {
265 }
266 }
267 GET_WINDOWS_FUNCTION(winsock2_module, WSAAddressToStringA);
268 #endif
269
270 GET_WINDOWS_FUNCTION(winsock_module, WSAAsyncSelect);
271 GET_WINDOWS_FUNCTION(winsock_module, WSAEventSelect);
272 /* We don't type-check select because at least some MinGW versions
273 * of the Windows API headers seem to disagree with the
274 * documentation on whether the 'struct timeval *' pointer is
275 * const or not. */
276 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, select);
277 GET_WINDOWS_FUNCTION(winsock_module, WSAGetLastError);
278 GET_WINDOWS_FUNCTION(winsock_module, WSAEnumNetworkEvents);
279 GET_WINDOWS_FUNCTION(winsock_module, WSAStartup);
280 GET_WINDOWS_FUNCTION(winsock_module, WSACleanup);
281 GET_WINDOWS_FUNCTION(winsock_module, closesocket);
282 GET_WINDOWS_FUNCTION(winsock_module, ntohl);
283 GET_WINDOWS_FUNCTION(winsock_module, htonl);
284 GET_WINDOWS_FUNCTION(winsock_module, htons);
285 GET_WINDOWS_FUNCTION(winsock_module, ntohs);
286 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, gethostname);
287 GET_WINDOWS_FUNCTION(winsock_module, gethostbyname);
288 GET_WINDOWS_FUNCTION(winsock_module, getservbyname);
289 GET_WINDOWS_FUNCTION(winsock_module, inet_addr);
290 GET_WINDOWS_FUNCTION(winsock_module, inet_ntoa);
291 /* Older Visual Studio, and MinGW as of Ubuntu 16.04, don't know
292 * about this function at all, so can't type-check it. Also there
293 * seems to be some disagreement in the VS headers about whether
294 * the second argument is void * or const void *, so I omit the
295 * type check. */
296 GET_WINDOWS_FUNCTION_NO_TYPECHECK(winsock_module, inet_ntop);
297 GET_WINDOWS_FUNCTION(winsock_module, connect);
298 GET_WINDOWS_FUNCTION(winsock_module, bind);
299 GET_WINDOWS_FUNCTION(winsock_module, setsockopt);
300 GET_WINDOWS_FUNCTION(winsock_module, socket);
301 GET_WINDOWS_FUNCTION(winsock_module, listen);
302 GET_WINDOWS_FUNCTION(winsock_module, send);
303 GET_WINDOWS_FUNCTION(winsock_module, shutdown);
304 GET_WINDOWS_FUNCTION(winsock_module, ioctlsocket);
305 GET_WINDOWS_FUNCTION(winsock_module, accept);
306 GET_WINDOWS_FUNCTION(winsock_module, getpeername);
307 GET_WINDOWS_FUNCTION(winsock_module, recv);
308 GET_WINDOWS_FUNCTION(winsock_module, WSAIoctl);
309
310 /* Try to get the best WinSock version we can get */
311 if (!sk_startup(2,2) &&
312 !sk_startup(2,0) &&
313 !sk_startup(1,1)) {
314 modalfatalbox("Unable to initialise WinSock");
315 }
316
317 sktree = newtree234(cmpfortree);
318 }
319
sk_cleanup(void)320 void sk_cleanup(void)
321 {
322 NetSocket *s;
323 int i;
324
325 if (sktree) {
326 for (i = 0; (s = index234(sktree, i)) != NULL; i++) {
327 p_closesocket(s->s);
328 }
329 freetree234(sktree);
330 sktree = NULL;
331 }
332
333 if (p_WSACleanup)
334 p_WSACleanup();
335 if (winsock_module)
336 FreeLibrary(winsock_module);
337 #ifndef NO_IPV6
338 if (wship6_module)
339 FreeLibrary(wship6_module);
340 #endif
341 }
342
winsock_error_string(int error)343 const char *winsock_error_string(int error)
344 {
345 /*
346 * Error codes we know about and have historically had reasonably
347 * sensible error messages for.
348 */
349 switch (error) {
350 case WSAEACCES:
351 return "Network error: Permission denied";
352 case WSAEADDRINUSE:
353 return "Network error: Address already in use";
354 case WSAEADDRNOTAVAIL:
355 return "Network error: Cannot assign requested address";
356 case WSAEAFNOSUPPORT:
357 return
358 "Network error: Address family not supported by protocol family";
359 case WSAEALREADY:
360 return "Network error: Operation already in progress";
361 case WSAECONNABORTED:
362 return "Network error: Software caused connection abort";
363 case WSAECONNREFUSED:
364 return "Network error: Connection refused";
365 case WSAECONNRESET:
366 return "Network error: Connection reset by peer";
367 case WSAEDESTADDRREQ:
368 return "Network error: Destination address required";
369 case WSAEFAULT:
370 return "Network error: Bad address";
371 case WSAEHOSTDOWN:
372 return "Network error: Host is down";
373 case WSAEHOSTUNREACH:
374 return "Network error: No route to host";
375 case WSAEINPROGRESS:
376 return "Network error: Operation now in progress";
377 case WSAEINTR:
378 return "Network error: Interrupted function call";
379 case WSAEINVAL:
380 return "Network error: Invalid argument";
381 case WSAEISCONN:
382 return "Network error: Socket is already connected";
383 case WSAEMFILE:
384 return "Network error: Too many open files";
385 case WSAEMSGSIZE:
386 return "Network error: Message too long";
387 case WSAENETDOWN:
388 return "Network error: Network is down";
389 case WSAENETRESET:
390 return "Network error: Network dropped connection on reset";
391 case WSAENETUNREACH:
392 return "Network error: Network is unreachable";
393 case WSAENOBUFS:
394 return "Network error: No buffer space available";
395 case WSAENOPROTOOPT:
396 return "Network error: Bad protocol option";
397 case WSAENOTCONN:
398 return "Network error: Socket is not connected";
399 case WSAENOTSOCK:
400 return "Network error: Socket operation on non-socket";
401 case WSAEOPNOTSUPP:
402 return "Network error: Operation not supported";
403 case WSAEPFNOSUPPORT:
404 return "Network error: Protocol family not supported";
405 case WSAEPROCLIM:
406 return "Network error: Too many processes";
407 case WSAEPROTONOSUPPORT:
408 return "Network error: Protocol not supported";
409 case WSAEPROTOTYPE:
410 return "Network error: Protocol wrong type for socket";
411 case WSAESHUTDOWN:
412 return "Network error: Cannot send after socket shutdown";
413 case WSAESOCKTNOSUPPORT:
414 return "Network error: Socket type not supported";
415 case WSAETIMEDOUT:
416 return "Network error: Connection timed out";
417 case WSAEWOULDBLOCK:
418 return "Network error: Resource temporarily unavailable";
419 case WSAEDISCON:
420 return "Network error: Graceful shutdown in progress";
421 }
422
423 /*
424 * Handle any other error code by delegating to win_strerror.
425 */
426 return win_strerror(error);
427 }
428
sk_namelookup(const char * host,char ** canonicalname,int address_family)429 SockAddr *sk_namelookup(const char *host, char **canonicalname,
430 int address_family)
431 {
432 SockAddr *ret = snew(SockAddr);
433 unsigned long a;
434 char realhost[8192];
435 int hint_family;
436
437 /* Default to IPv4. */
438 hint_family = (address_family == ADDRTYPE_IPV4 ? AF_INET :
439 #ifndef NO_IPV6
440 address_family == ADDRTYPE_IPV6 ? AF_INET6 :
441 #endif
442 AF_UNSPEC);
443
444 /* Clear the structure and default to IPv4. */
445 memset(ret, 0, sizeof(SockAddr));
446 #ifndef NO_IPV6
447 ret->ais = NULL;
448 #endif
449 ret->namedpipe = false;
450 ret->addresses = NULL;
451 ret->resolved = false;
452 ret->refcount = 1;
453 *realhost = '\0';
454
455 if ((a = p_inet_addr(host)) == (unsigned long) INADDR_NONE) {
456 struct hostent *h = NULL;
457 int err = 0;
458 #ifndef NO_IPV6
459 /*
460 * Use getaddrinfo when it's available
461 */
462 if (p_getaddrinfo) {
463 struct addrinfo hints;
464 memset(&hints, 0, sizeof(hints));
465 hints.ai_family = hint_family;
466 hints.ai_flags = AI_CANONNAME;
467 {
468 /* strip [] on IPv6 address literals */
469 char *trimmed_host = host_strduptrim(host);
470 err = p_getaddrinfo(trimmed_host, NULL, &hints, &ret->ais);
471 sfree(trimmed_host);
472 }
473 if (err == 0)
474 ret->resolved = true;
475 } else
476 #endif
477 {
478 /*
479 * Otherwise use the IPv4-only gethostbyname...
480 * (NOTE: we don't use gethostbyname as a fallback!)
481 */
482 if ( (h = p_gethostbyname(host)) )
483 ret->resolved = true;
484 else
485 err = p_WSAGetLastError();
486 }
487
488 if (!ret->resolved) {
489 ret->error = (err == WSAENETDOWN ? "Network is down" :
490 err == WSAHOST_NOT_FOUND ? "Host does not exist" :
491 err == WSATRY_AGAIN ? "Host not found" :
492 #ifndef NO_IPV6
493 p_getaddrinfo&&p_gai_strerror ? p_gai_strerror(err) :
494 #endif
495 "gethostbyname: unknown error");
496 } else {
497 ret->error = NULL;
498
499 #ifndef NO_IPV6
500 /* If we got an address info use that... */
501 if (ret->ais) {
502 /* Are we in IPv4 fallback mode? */
503 /* We put the IPv4 address into the a variable so we can further-on use the IPv4 code... */
504 if (ret->ais->ai_family == AF_INET)
505 memcpy(&a,
506 (char *) &((SOCKADDR_IN *) ret->ais->
507 ai_addr)->sin_addr, sizeof(a));
508
509 if (ret->ais->ai_canonname)
510 strncpy(realhost, ret->ais->ai_canonname, lenof(realhost));
511 else
512 strncpy(realhost, host, lenof(realhost));
513 }
514 /* We used the IPv4-only gethostbyname()... */
515 else
516 #endif
517 {
518 int n;
519 for (n = 0; h->h_addr_list[n]; n++);
520 ret->addresses = snewn(n, unsigned long);
521 ret->naddresses = n;
522 for (n = 0; n < ret->naddresses; n++) {
523 memcpy(&a, h->h_addr_list[n], sizeof(a));
524 ret->addresses[n] = p_ntohl(a);
525 }
526 memcpy(&a, h->h_addr, sizeof(a));
527 /* This way we are always sure the h->h_name is valid :) */
528 strncpy(realhost, h->h_name, sizeof(realhost));
529 }
530 }
531 } else {
532 /*
533 * This must be a numeric IPv4 address because it caused a
534 * success return from inet_addr.
535 */
536 ret->addresses = snewn(1, unsigned long);
537 ret->naddresses = 1;
538 ret->addresses[0] = p_ntohl(a);
539 ret->resolved = true;
540 strncpy(realhost, host, sizeof(realhost));
541 }
542 realhost[lenof(realhost)-1] = '\0';
543 *canonicalname = dupstr(realhost);
544 return ret;
545 }
546
sk_nonamelookup(const char * host)547 SockAddr *sk_nonamelookup(const char *host)
548 {
549 SockAddr *ret = snew(SockAddr);
550 ret->error = NULL;
551 ret->resolved = false;
552 #ifndef NO_IPV6
553 ret->ais = NULL;
554 #endif
555 ret->namedpipe = false;
556 ret->addresses = NULL;
557 ret->naddresses = 0;
558 ret->refcount = 1;
559 strncpy(ret->hostname, host, lenof(ret->hostname));
560 ret->hostname[lenof(ret->hostname)-1] = '\0';
561 return ret;
562 }
563
sk_namedpipe_addr(const char * pipename)564 SockAddr *sk_namedpipe_addr(const char *pipename)
565 {
566 SockAddr *ret = snew(SockAddr);
567 ret->error = NULL;
568 ret->resolved = false;
569 #ifndef NO_IPV6
570 ret->ais = NULL;
571 #endif
572 ret->namedpipe = true;
573 ret->addresses = NULL;
574 ret->naddresses = 0;
575 ret->refcount = 1;
576 strncpy(ret->hostname, pipename, lenof(ret->hostname));
577 ret->hostname[lenof(ret->hostname)-1] = '\0';
578 return ret;
579 }
580
sk_nextaddr(SockAddr * addr,SockAddrStep * step)581 static bool sk_nextaddr(SockAddr *addr, SockAddrStep *step)
582 {
583 #ifndef NO_IPV6
584 if (step->ai) {
585 if (step->ai->ai_next) {
586 step->ai = step->ai->ai_next;
587 return true;
588 } else
589 return false;
590 }
591 #endif
592 if (step->curraddr+1 < addr->naddresses) {
593 step->curraddr++;
594 return true;
595 } else {
596 return false;
597 }
598 }
599
sk_getaddr(SockAddr * addr,char * buf,int buflen)600 void sk_getaddr(SockAddr *addr, char *buf, int buflen)
601 {
602 SockAddrStep step;
603 START_STEP(addr, step);
604
605 #ifndef NO_IPV6
606 if (step.ai) {
607 int err = 0;
608 if (p_WSAAddressToStringA) {
609 DWORD dwbuflen = buflen;
610 err = p_WSAAddressToStringA(step.ai->ai_addr, step.ai->ai_addrlen,
611 NULL, buf, &dwbuflen);
612 } else
613 err = -1;
614 if (err) {
615 strncpy(buf, addr->hostname, buflen);
616 if (!buf[0])
617 strncpy(buf, "<unknown>", buflen);
618 buf[buflen-1] = '\0';
619 }
620 } else
621 #endif
622 if (SOCKADDR_FAMILY(addr, step) == AF_INET) {
623 struct in_addr a;
624 assert(addr->addresses && step.curraddr < addr->naddresses);
625 a.s_addr = p_htonl(addr->addresses[step.curraddr]);
626 strncpy(buf, p_inet_ntoa(a), buflen);
627 buf[buflen-1] = '\0';
628 } else {
629 strncpy(buf, addr->hostname, buflen);
630 buf[buflen-1] = '\0';
631 }
632 }
633
634 /*
635 * This constructs a SockAddr that points at one specific sub-address
636 * of a parent SockAddr. The returned SockAddr does not own all its
637 * own memory: it points into the old one's data structures, so it
638 * MUST NOT be used after the old one is freed, and it MUST NOT be
639 * passed to sk_addr_free. (The latter is why it's returned by value
640 * rather than dynamically allocated - that should clue in anyone
641 * writing a call to it that something is weird about it.)
642 */
sk_extractaddr_tmp(SockAddr * addr,const SockAddrStep * step)643 static SockAddr sk_extractaddr_tmp(
644 SockAddr *addr, const SockAddrStep *step)
645 {
646 SockAddr toret;
647 toret = *addr; /* structure copy */
648 toret.refcount = 1;
649
650 #ifndef NO_IPV6
651 toret.ais = step->ai;
652 #endif
653 if (SOCKADDR_FAMILY(addr, *step) == AF_INET
654 #ifndef NO_IPV6
655 && !toret.ais
656 #endif
657 )
658 toret.addresses += step->curraddr;
659
660 return toret;
661 }
662
sk_addr_needs_port(SockAddr * addr)663 bool sk_addr_needs_port(SockAddr *addr)
664 {
665 return !addr->namedpipe;
666 }
667
sk_hostname_is_local(const char * name)668 bool sk_hostname_is_local(const char *name)
669 {
670 return !strcmp(name, "localhost") ||
671 !strcmp(name, "::1") ||
672 !strncmp(name, "127.", 4);
673 }
674
675 static INTERFACE_INFO local_interfaces[16];
676 static int n_local_interfaces; /* 0=not yet, -1=failed, >0=number */
677
ipv4_is_local_addr(struct in_addr addr)678 static bool ipv4_is_local_addr(struct in_addr addr)
679 {
680 if (ipv4_is_loopback(addr))
681 return true; /* loopback addresses are local */
682 if (!n_local_interfaces) {
683 SOCKET s = p_socket(AF_INET, SOCK_DGRAM, 0);
684 DWORD retbytes;
685
686 SetHandleInformation((HANDLE)s, HANDLE_FLAG_INHERIT, 0);
687
688 if (p_WSAIoctl &&
689 p_WSAIoctl(s, SIO_GET_INTERFACE_LIST, NULL, 0,
690 local_interfaces, sizeof(local_interfaces),
691 &retbytes, NULL, NULL) == 0)
692 n_local_interfaces = retbytes / sizeof(INTERFACE_INFO);
693 else
694 n_local_interfaces = -1;
695 }
696 if (n_local_interfaces > 0) {
697 int i;
698 for (i = 0; i < n_local_interfaces; i++) {
699 SOCKADDR_IN *address =
700 (SOCKADDR_IN *)&local_interfaces[i].iiAddress;
701 if (address->sin_addr.s_addr == addr.s_addr)
702 return true; /* this address is local */
703 }
704 }
705 return false; /* this address is not local */
706 }
707
sk_address_is_local(SockAddr * addr)708 bool sk_address_is_local(SockAddr *addr)
709 {
710 SockAddrStep step;
711 int family;
712 START_STEP(addr, step);
713 family = SOCKADDR_FAMILY(addr, step);
714
715 #ifndef NO_IPV6
716 if (family == AF_INET6) {
717 return IN6_IS_ADDR_LOOPBACK(&((const struct sockaddr_in6 *)step.ai->ai_addr)->sin6_addr);
718 } else
719 #endif
720 if (family == AF_INET) {
721 #ifndef NO_IPV6
722 if (step.ai) {
723 return ipv4_is_local_addr(((struct sockaddr_in *)step.ai->ai_addr)
724 ->sin_addr);
725 } else
726 #endif
727 {
728 struct in_addr a;
729 assert(addr->addresses && step.curraddr < addr->naddresses);
730 a.s_addr = p_htonl(addr->addresses[step.curraddr]);
731 return ipv4_is_local_addr(a);
732 }
733 } else {
734 assert(family == AF_UNSPEC);
735 return false; /* we don't know; assume not */
736 }
737 }
738
sk_address_is_special_local(SockAddr * addr)739 bool sk_address_is_special_local(SockAddr *addr)
740 {
741 return false; /* no Unix-domain socket analogue here */
742 }
743
sk_addrtype(SockAddr * addr)744 int sk_addrtype(SockAddr *addr)
745 {
746 SockAddrStep step;
747 int family;
748 START_STEP(addr, step);
749 family = SOCKADDR_FAMILY(addr, step);
750
751 return (family == AF_INET ? ADDRTYPE_IPV4 :
752 #ifndef NO_IPV6
753 family == AF_INET6 ? ADDRTYPE_IPV6 :
754 #endif
755 ADDRTYPE_NAME);
756 }
757
sk_addrcopy(SockAddr * addr,char * buf)758 void sk_addrcopy(SockAddr *addr, char *buf)
759 {
760 SockAddrStep step;
761 int family;
762 START_STEP(addr, step);
763 family = SOCKADDR_FAMILY(addr, step);
764
765 assert(family != AF_UNSPEC);
766 #ifndef NO_IPV6
767 if (step.ai) {
768 if (family == AF_INET)
769 memcpy(buf, &((struct sockaddr_in *)step.ai->ai_addr)->sin_addr,
770 sizeof(struct in_addr));
771 else if (family == AF_INET6)
772 memcpy(buf, &((struct sockaddr_in6 *)step.ai->ai_addr)->sin6_addr,
773 sizeof(struct in6_addr));
774 else
775 unreachable("bad address family in sk_addrcopy");
776 } else
777 #endif
778 if (family == AF_INET) {
779 struct in_addr a;
780 assert(addr->addresses && step.curraddr < addr->naddresses);
781 a.s_addr = p_htonl(addr->addresses[step.curraddr]);
782 memcpy(buf, (char*) &a.s_addr, 4);
783 }
784 }
785
sk_addr_free(SockAddr * addr)786 void sk_addr_free(SockAddr *addr)
787 {
788 if (--addr->refcount > 0)
789 return;
790 #ifndef NO_IPV6
791 if (addr->ais && p_freeaddrinfo)
792 p_freeaddrinfo(addr->ais);
793 #endif
794 if (addr->addresses)
795 sfree(addr->addresses);
796 sfree(addr);
797 }
798
sk_addr_dup(SockAddr * addr)799 SockAddr *sk_addr_dup(SockAddr *addr)
800 {
801 addr->refcount++;
802 return addr;
803 }
804
sk_net_plug(Socket * sock,Plug * p)805 static Plug *sk_net_plug(Socket *sock, Plug *p)
806 {
807 NetSocket *s = container_of(sock, NetSocket, sock);
808 Plug *ret = s->plug;
809 if (p)
810 s->plug = p;
811 return ret;
812 }
813
814 static void sk_net_close(Socket *s);
815 static size_t sk_net_write(Socket *s, const void *data, size_t len);
816 static size_t sk_net_write_oob(Socket *s, const void *data, size_t len);
817 static void sk_net_write_eof(Socket *s);
818 static void sk_net_set_frozen(Socket *s, bool is_frozen);
819 static const char *sk_net_socket_error(Socket *s);
820 static SocketPeerInfo *sk_net_peer_info(Socket *s);
821
822 static const SocketVtable NetSocket_sockvt = {
823 .plug = sk_net_plug,
824 .close = sk_net_close,
825 .write = sk_net_write,
826 .write_oob = sk_net_write_oob,
827 .write_eof = sk_net_write_eof,
828 .set_frozen = sk_net_set_frozen,
829 .socket_error = sk_net_socket_error,
830 .peer_info = sk_net_peer_info,
831 };
832
sk_net_accept(accept_ctx_t ctx,Plug * plug)833 static Socket *sk_net_accept(accept_ctx_t ctx, Plug *plug)
834 {
835 DWORD err;
836 const char *errstr;
837 NetSocket *ret;
838
839 /*
840 * Create NetSocket structure.
841 */
842 ret = snew(NetSocket);
843 ret->sock.vt = &NetSocket_sockvt;
844 ret->error = NULL;
845 ret->plug = plug;
846 bufchain_init(&ret->output_data);
847 ret->writable = true; /* to start with */
848 ret->sending_oob = 0;
849 ret->outgoingeof = EOF_NO;
850 ret->frozen = true;
851 ret->frozen_readable = false;
852 ret->localhost_only = false; /* unused, but best init anyway */
853 ret->pending_error = 0;
854 ret->parent = ret->child = NULL;
855 ret->addr = NULL;
856
857 ret->s = (SOCKET)ctx.p;
858
859 if (ret->s == INVALID_SOCKET) {
860 err = p_WSAGetLastError();
861 ret->error = winsock_error_string(err);
862 return &ret->sock;
863 }
864
865 ret->oobinline = false;
866
867 /* Set up a select mechanism. This could be an AsyncSelect on a
868 * window, or an EventSelect on an event object. */
869 errstr = do_select(ret->s, true);
870 if (errstr) {
871 ret->error = errstr;
872 return &ret->sock;
873 }
874
875 add234(sktree, ret);
876
877 return &ret->sock;
878 }
879
try_connect(NetSocket * sock)880 static DWORD try_connect(NetSocket *sock)
881 {
882 SOCKET s;
883 #ifndef NO_IPV6
884 SOCKADDR_IN6 a6;
885 #endif
886 SOCKADDR_IN a;
887 DWORD err;
888 const char *errstr;
889 short localport;
890 int family;
891
892 if (sock->s != INVALID_SOCKET) {
893 do_select(sock->s, false);
894 p_closesocket(sock->s);
895 }
896
897 {
898 SockAddr thisaddr = sk_extractaddr_tmp(
899 sock->addr, &sock->step);
900 plug_log(sock->plug, PLUGLOG_CONNECT_TRYING,
901 &thisaddr, sock->port, NULL, 0);
902 }
903
904 /*
905 * Open socket.
906 */
907 family = SOCKADDR_FAMILY(sock->addr, sock->step);
908
909 /*
910 * Remove the socket from the tree before we overwrite its
911 * internal socket id, because that forms part of the tree's
912 * sorting criterion. We'll add it back before exiting this
913 * function, whether we changed anything or not.
914 */
915 del234(sktree, sock);
916
917 s = p_socket(family, SOCK_STREAM, 0);
918 sock->s = s;
919
920 if (s == INVALID_SOCKET) {
921 err = p_WSAGetLastError();
922 sock->error = winsock_error_string(err);
923 goto ret;
924 }
925
926 SetHandleInformation((HANDLE)s, HANDLE_FLAG_INHERIT, 0);
927
928 if (sock->oobinline) {
929 BOOL b = true;
930 p_setsockopt(s, SOL_SOCKET, SO_OOBINLINE, (void *) &b, sizeof(b));
931 }
932
933 if (sock->nodelay) {
934 BOOL b = true;
935 p_setsockopt(s, IPPROTO_TCP, TCP_NODELAY, (void *) &b, sizeof(b));
936 }
937
938 if (sock->keepalive) {
939 BOOL b = true;
940 p_setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, (void *) &b, sizeof(b));
941 }
942
943 /*
944 * Bind to local address.
945 */
946 if (sock->privport)
947 localport = 1023; /* count from 1023 downwards */
948 else
949 localport = 0; /* just use port 0 (ie winsock picks) */
950
951 /* Loop round trying to bind */
952 while (1) {
953 int sockcode;
954
955 #ifndef NO_IPV6
956 if (family == AF_INET6) {
957 memset(&a6, 0, sizeof(a6));
958 a6.sin6_family = AF_INET6;
959 /*a6.sin6_addr = in6addr_any; */ /* == 0 done by memset() */
960 a6.sin6_port = p_htons(localport);
961 } else
962 #endif
963 {
964 a.sin_family = AF_INET;
965 a.sin_addr.s_addr = p_htonl(INADDR_ANY);
966 a.sin_port = p_htons(localport);
967 }
968 #ifndef NO_IPV6
969 sockcode = p_bind(s, (family == AF_INET6 ?
970 (struct sockaddr *) &a6 :
971 (struct sockaddr *) &a),
972 (family == AF_INET6 ? sizeof(a6) : sizeof(a)));
973 #else
974 sockcode = p_bind(s, (struct sockaddr *) &a, sizeof(a));
975 #endif
976 if (sockcode != SOCKET_ERROR) {
977 err = 0;
978 break; /* done */
979 } else {
980 err = p_WSAGetLastError();
981 if (err != WSAEADDRINUSE) /* failed, for a bad reason */
982 break;
983 }
984
985 if (localport == 0)
986 break; /* we're only looping once */
987 localport--;
988 if (localport == 0)
989 break; /* we might have got to the end */
990 }
991
992 if (err) {
993 sock->error = winsock_error_string(err);
994 goto ret;
995 }
996
997 /*
998 * Connect to remote address.
999 */
1000 #ifndef NO_IPV6
1001 if (sock->step.ai) {
1002 if (family == AF_INET6) {
1003 a6.sin6_family = AF_INET6;
1004 a6.sin6_port = p_htons((short) sock->port);
1005 a6.sin6_addr =
1006 ((struct sockaddr_in6 *) sock->step.ai->ai_addr)->sin6_addr;
1007 a6.sin6_flowinfo = ((struct sockaddr_in6 *) sock->step.ai->ai_addr)->sin6_flowinfo;
1008 a6.sin6_scope_id = ((struct sockaddr_in6 *) sock->step.ai->ai_addr)->sin6_scope_id;
1009 } else {
1010 a.sin_family = AF_INET;
1011 a.sin_addr =
1012 ((struct sockaddr_in *) sock->step.ai->ai_addr)->sin_addr;
1013 a.sin_port = p_htons((short) sock->port);
1014 }
1015 } else
1016 #endif
1017 {
1018 assert(sock->addr->addresses && sock->step.curraddr < sock->addr->naddresses);
1019 a.sin_family = AF_INET;
1020 a.sin_addr.s_addr = p_htonl(sock->addr->addresses[sock->step.curraddr]);
1021 a.sin_port = p_htons((short) sock->port);
1022 }
1023
1024 /* Set up a select mechanism. This could be an AsyncSelect on a
1025 * window, or an EventSelect on an event object. */
1026 errstr = do_select(s, true);
1027 if (errstr) {
1028 sock->error = errstr;
1029 err = 1;
1030 goto ret;
1031 }
1032
1033 if ((
1034 #ifndef NO_IPV6
1035 p_connect(s,
1036 ((family == AF_INET6) ? (struct sockaddr *) &a6 :
1037 (struct sockaddr *) &a),
1038 (family == AF_INET6) ? sizeof(a6) : sizeof(a))
1039 #else
1040 p_connect(s, (struct sockaddr *) &a, sizeof(a))
1041 #endif
1042 ) == SOCKET_ERROR) {
1043 err = p_WSAGetLastError();
1044 /*
1045 * We expect a potential EWOULDBLOCK here, because the
1046 * chances are the front end has done a select for
1047 * FD_CONNECT, so that connect() will complete
1048 * asynchronously.
1049 */
1050 if ( err != WSAEWOULDBLOCK ) {
1051 sock->error = winsock_error_string(err);
1052 goto ret;
1053 }
1054 } else {
1055 /*
1056 * If we _don't_ get EWOULDBLOCK, the connect has completed
1057 * and we should set the socket as writable.
1058 */
1059 sock->writable = true;
1060 SockAddr thisaddr = sk_extractaddr_tmp(sock->addr, &sock->step);
1061 plug_log(sock->plug, PLUGLOG_CONNECT_SUCCESS,
1062 &thisaddr, sock->port, NULL, 0);
1063 }
1064
1065 err = 0;
1066
1067 ret:
1068
1069 /*
1070 * No matter what happened, put the socket back in the tree.
1071 */
1072 add234(sktree, sock);
1073
1074 if (err) {
1075 SockAddr thisaddr = sk_extractaddr_tmp(
1076 sock->addr, &sock->step);
1077 plug_log(sock->plug, PLUGLOG_CONNECT_FAILED,
1078 &thisaddr, sock->port, sock->error, err);
1079 }
1080 return err;
1081 }
1082
sk_new(SockAddr * addr,int port,bool privport,bool oobinline,bool nodelay,bool keepalive,Plug * plug)1083 Socket *sk_new(SockAddr *addr, int port, bool privport, bool oobinline,
1084 bool nodelay, bool keepalive, Plug *plug)
1085 {
1086 NetSocket *ret;
1087 DWORD err;
1088
1089 /*
1090 * Create NetSocket structure.
1091 */
1092 ret = snew(NetSocket);
1093 ret->sock.vt = &NetSocket_sockvt;
1094 ret->error = NULL;
1095 ret->plug = plug;
1096 bufchain_init(&ret->output_data);
1097 ret->connected = false; /* to start with */
1098 ret->writable = false; /* to start with */
1099 ret->sending_oob = 0;
1100 ret->outgoingeof = EOF_NO;
1101 ret->frozen = false;
1102 ret->frozen_readable = false;
1103 ret->localhost_only = false; /* unused, but best init anyway */
1104 ret->pending_error = 0;
1105 ret->parent = ret->child = NULL;
1106 ret->oobinline = oobinline;
1107 ret->nodelay = nodelay;
1108 ret->keepalive = keepalive;
1109 ret->privport = privport;
1110 ret->port = port;
1111 ret->addr = addr;
1112 START_STEP(ret->addr, ret->step);
1113 ret->s = INVALID_SOCKET;
1114
1115 err = 0;
1116 do {
1117 err = try_connect(ret);
1118 } while (err && sk_nextaddr(ret->addr, &ret->step));
1119
1120 return &ret->sock;
1121 }
1122
sk_newlistener(const char * srcaddr,int port,Plug * plug,bool local_host_only,int orig_address_family)1123 Socket *sk_newlistener(const char *srcaddr, int port, Plug *plug,
1124 bool local_host_only, int orig_address_family)
1125 {
1126 SOCKET s;
1127 #ifndef NO_IPV6
1128 SOCKADDR_IN6 a6;
1129 #endif
1130 SOCKADDR_IN a;
1131
1132 DWORD err;
1133 const char *errstr;
1134 NetSocket *ret;
1135 int retcode;
1136
1137 int address_family;
1138
1139 /*
1140 * Create NetSocket structure.
1141 */
1142 ret = snew(NetSocket);
1143 ret->sock.vt = &NetSocket_sockvt;
1144 ret->error = NULL;
1145 ret->plug = plug;
1146 bufchain_init(&ret->output_data);
1147 ret->writable = false; /* to start with */
1148 ret->sending_oob = 0;
1149 ret->outgoingeof = EOF_NO;
1150 ret->frozen = false;
1151 ret->frozen_readable = false;
1152 ret->localhost_only = local_host_only;
1153 ret->pending_error = 0;
1154 ret->parent = ret->child = NULL;
1155 ret->addr = NULL;
1156
1157 /*
1158 * Translate address_family from platform-independent constants
1159 * into local reality.
1160 */
1161 address_family = (orig_address_family == ADDRTYPE_IPV4 ? AF_INET :
1162 #ifndef NO_IPV6
1163 orig_address_family == ADDRTYPE_IPV6 ? AF_INET6 :
1164 #endif
1165 AF_UNSPEC);
1166
1167 /*
1168 * Our default, if passed the `don't care' value
1169 * ADDRTYPE_UNSPEC, is to listen on IPv4. If IPv6 is supported,
1170 * we will also set up a second socket listening on IPv6, but
1171 * the v4 one is primary since that ought to work even on
1172 * non-v6-supporting systems.
1173 */
1174 if (address_family == AF_UNSPEC) address_family = AF_INET;
1175
1176 /*
1177 * Open socket.
1178 */
1179 s = p_socket(address_family, SOCK_STREAM, 0);
1180 ret->s = s;
1181
1182 if (s == INVALID_SOCKET) {
1183 err = p_WSAGetLastError();
1184 ret->error = winsock_error_string(err);
1185 return &ret->sock;
1186 }
1187
1188 SetHandleInformation((HANDLE)s, HANDLE_FLAG_INHERIT, 0);
1189
1190 ret->oobinline = false;
1191
1192 {
1193 BOOL on = true;
1194 p_setsockopt(s, SOL_SOCKET, SO_EXCLUSIVEADDRUSE,
1195 (const char *)&on, sizeof(on));
1196 }
1197
1198 #ifndef NO_IPV6
1199 if (address_family == AF_INET6) {
1200 memset(&a6, 0, sizeof(a6));
1201 a6.sin6_family = AF_INET6;
1202 if (local_host_only)
1203 a6.sin6_addr = in6addr_loopback;
1204 else
1205 a6.sin6_addr = in6addr_any;
1206 if (srcaddr != NULL && p_getaddrinfo) {
1207 struct addrinfo hints;
1208 struct addrinfo *ai;
1209 int err;
1210
1211 memset(&hints, 0, sizeof(hints));
1212 hints.ai_family = AF_INET6;
1213 hints.ai_flags = 0;
1214 {
1215 /* strip [] on IPv6 address literals */
1216 char *trimmed_addr = host_strduptrim(srcaddr);
1217 err = p_getaddrinfo(trimmed_addr, NULL, &hints, &ai);
1218 sfree(trimmed_addr);
1219 }
1220 if (err == 0 && ai->ai_family == AF_INET6) {
1221 a6.sin6_addr =
1222 ((struct sockaddr_in6 *)ai->ai_addr)->sin6_addr;
1223 }
1224 }
1225 a6.sin6_port = p_htons(port);
1226 } else
1227 #endif
1228 {
1229 bool got_addr = false;
1230 a.sin_family = AF_INET;
1231
1232 /*
1233 * Bind to source address. First try an explicitly
1234 * specified one...
1235 */
1236 if (srcaddr) {
1237 a.sin_addr.s_addr = p_inet_addr(srcaddr);
1238 if (a.sin_addr.s_addr != INADDR_NONE) {
1239 /* Override localhost_only with specified listen addr. */
1240 ret->localhost_only = ipv4_is_loopback(a.sin_addr);
1241 got_addr = true;
1242 }
1243 }
1244
1245 /*
1246 * ... and failing that, go with one of the standard ones.
1247 */
1248 if (!got_addr) {
1249 if (local_host_only)
1250 a.sin_addr.s_addr = p_htonl(INADDR_LOOPBACK);
1251 else
1252 a.sin_addr.s_addr = p_htonl(INADDR_ANY);
1253 }
1254
1255 a.sin_port = p_htons((short)port);
1256 }
1257 #ifndef NO_IPV6
1258 retcode = p_bind(s, (address_family == AF_INET6 ?
1259 (struct sockaddr *) &a6 :
1260 (struct sockaddr *) &a),
1261 (address_family ==
1262 AF_INET6 ? sizeof(a6) : sizeof(a)));
1263 #else
1264 retcode = p_bind(s, (struct sockaddr *) &a, sizeof(a));
1265 #endif
1266 if (retcode != SOCKET_ERROR) {
1267 err = 0;
1268 } else {
1269 err = p_WSAGetLastError();
1270 }
1271
1272 if (err) {
1273 p_closesocket(s);
1274 ret->error = winsock_error_string(err);
1275 return &ret->sock;
1276 }
1277
1278
1279 if (p_listen(s, SOMAXCONN) == SOCKET_ERROR) {
1280 p_closesocket(s);
1281 ret->error = winsock_error_string(p_WSAGetLastError());
1282 return &ret->sock;
1283 }
1284
1285 /* Set up a select mechanism. This could be an AsyncSelect on a
1286 * window, or an EventSelect on an event object. */
1287 errstr = do_select(s, true);
1288 if (errstr) {
1289 p_closesocket(s);
1290 ret->error = errstr;
1291 return &ret->sock;
1292 }
1293
1294 add234(sktree, ret);
1295
1296 #ifndef NO_IPV6
1297 /*
1298 * If we were given ADDRTYPE_UNSPEC, we must also create an
1299 * IPv6 listening socket and link it to this one.
1300 */
1301 if (address_family == AF_INET && orig_address_family == ADDRTYPE_UNSPEC) {
1302 Socket *other = sk_newlistener(srcaddr, port, plug,
1303 local_host_only, ADDRTYPE_IPV6);
1304
1305 if (other) {
1306 NetSocket *ns = container_of(other, NetSocket, sock);
1307 if (!ns->error) {
1308 ns->parent = ret;
1309 ret->child = ns;
1310 } else {
1311 sfree(ns);
1312 }
1313 }
1314 }
1315 #endif
1316
1317 return &ret->sock;
1318 }
1319
sk_net_close(Socket * sock)1320 static void sk_net_close(Socket *sock)
1321 {
1322 NetSocket *s = container_of(sock, NetSocket, sock);
1323
1324 if (s->child)
1325 sk_net_close(&s->child->sock);
1326
1327 bufchain_clear(&s->output_data);
1328
1329 del234(sktree, s);
1330 do_select(s->s, false);
1331 p_closesocket(s->s);
1332 if (s->addr)
1333 sk_addr_free(s->addr);
1334 delete_callbacks_for_context(s);
1335 sfree(s);
1336 }
1337
1338 /*
1339 * Deal with socket errors detected in try_send().
1340 */
socket_error_callback(void * vs)1341 static void socket_error_callback(void *vs)
1342 {
1343 NetSocket *s = (NetSocket *)vs;
1344
1345 /*
1346 * Just in case other socket work has caused this socket to vanish
1347 * or become somehow non-erroneous before this callback arrived...
1348 */
1349 if (!find234(sktree, s, NULL) || !s->pending_error)
1350 return;
1351
1352 /*
1353 * An error has occurred on this socket. Pass it to the plug.
1354 */
1355 plug_closing(s->plug, winsock_error_string(s->pending_error),
1356 s->pending_error, 0);
1357 }
1358
1359 /*
1360 * The function which tries to send on a socket once it's deemed
1361 * writable.
1362 */
try_send(NetSocket * s)1363 void try_send(NetSocket *s)
1364 {
1365 while (s->sending_oob || bufchain_size(&s->output_data) > 0) {
1366 int nsent;
1367 DWORD err;
1368 const void *data;
1369 size_t len;
1370 int urgentflag;
1371
1372 if (s->sending_oob) {
1373 urgentflag = MSG_OOB;
1374 len = s->sending_oob;
1375 data = &s->oobdata;
1376 } else {
1377 urgentflag = 0;
1378 ptrlen bufdata = bufchain_prefix(&s->output_data);
1379 data = bufdata.ptr;
1380 len = bufdata.len;
1381 }
1382 len = min(len, INT_MAX); /* WinSock send() takes an int */
1383 nsent = p_send(s->s, data, len, urgentflag);
1384 noise_ultralight(NOISE_SOURCE_IOLEN, nsent);
1385 if (nsent <= 0) {
1386 err = (nsent < 0 ? p_WSAGetLastError() : 0);
1387 if ((err < WSABASEERR && nsent < 0) || err == WSAEWOULDBLOCK) {
1388 /*
1389 * Perfectly normal: we've sent all we can for the moment.
1390 *
1391 * (Some WinSock send() implementations can return
1392 * <0 but leave no sensible error indication -
1393 * WSAGetLastError() is called but returns zero or
1394 * a small number - so we check that case and treat
1395 * it just like WSAEWOULDBLOCK.)
1396 */
1397 s->writable = false;
1398 return;
1399 } else {
1400 /*
1401 * If send() returns a socket error, we unfortunately
1402 * can't just call plug_closing(), because it's quite
1403 * likely that we're currently _in_ a call from the
1404 * code we'd be calling back to, so we'd have to make
1405 * half the SSH code reentrant. Instead we flag a
1406 * pending error on the socket, to be dealt with (by
1407 * calling plug_closing()) at some suitable future
1408 * moment.
1409 */
1410 s->pending_error = err;
1411 queue_toplevel_callback(socket_error_callback, s);
1412 return;
1413 }
1414 } else {
1415 if (s->sending_oob) {
1416 if (nsent < len) {
1417 memmove(s->oobdata, s->oobdata+nsent, len-nsent);
1418 s->sending_oob = len - nsent;
1419 } else {
1420 s->sending_oob = 0;
1421 }
1422 } else {
1423 bufchain_consume(&s->output_data, nsent);
1424 }
1425 }
1426 }
1427
1428 /*
1429 * If we reach here, we've finished sending everything we might
1430 * have needed to send. Send EOF, if we need to.
1431 */
1432 if (s->outgoingeof == EOF_PENDING) {
1433 p_shutdown(s->s, SD_SEND);
1434 s->outgoingeof = EOF_SENT;
1435 }
1436 }
1437
sk_net_write(Socket * sock,const void * buf,size_t len)1438 static size_t sk_net_write(Socket *sock, const void *buf, size_t len)
1439 {
1440 NetSocket *s = container_of(sock, NetSocket, sock);
1441
1442 assert(s->outgoingeof == EOF_NO);
1443
1444 /*
1445 * Add the data to the buffer list on the socket.
1446 */
1447 bufchain_add(&s->output_data, buf, len);
1448
1449 /*
1450 * Now try sending from the start of the buffer list.
1451 */
1452 if (s->writable)
1453 try_send(s);
1454
1455 return bufchain_size(&s->output_data);
1456 }
1457
sk_net_write_oob(Socket * sock,const void * buf,size_t len)1458 static size_t sk_net_write_oob(Socket *sock, const void *buf, size_t len)
1459 {
1460 NetSocket *s = container_of(sock, NetSocket, sock);
1461
1462 assert(s->outgoingeof == EOF_NO);
1463
1464 /*
1465 * Replace the buffer list on the socket with the data.
1466 */
1467 bufchain_clear(&s->output_data);
1468 assert(len <= sizeof(s->oobdata));
1469 memcpy(s->oobdata, buf, len);
1470 s->sending_oob = len;
1471
1472 /*
1473 * Now try sending from the start of the buffer list.
1474 */
1475 if (s->writable)
1476 try_send(s);
1477
1478 return s->sending_oob;
1479 }
1480
sk_net_write_eof(Socket * sock)1481 static void sk_net_write_eof(Socket *sock)
1482 {
1483 NetSocket *s = container_of(sock, NetSocket, sock);
1484
1485 assert(s->outgoingeof == EOF_NO);
1486
1487 /*
1488 * Mark the socket as pending outgoing EOF.
1489 */
1490 s->outgoingeof = EOF_PENDING;
1491
1492 /*
1493 * Now try sending from the start of the buffer list.
1494 */
1495 if (s->writable)
1496 try_send(s);
1497 }
1498
select_result(WPARAM wParam,LPARAM lParam)1499 void select_result(WPARAM wParam, LPARAM lParam)
1500 {
1501 int ret;
1502 DWORD err;
1503 char buf[20480]; /* nice big buffer for plenty of speed */
1504 NetSocket *s;
1505 bool atmark;
1506
1507 /* wParam is the socket itself */
1508
1509 if (wParam == 0)
1510 return; /* boggle */
1511
1512 s = find234(sktree, (void *) wParam, cmpforsearch);
1513 if (!s)
1514 return; /* boggle */
1515
1516 if ((err = WSAGETSELECTERROR(lParam)) != 0) {
1517 /*
1518 * An error has occurred on this socket. Pass it to the
1519 * plug.
1520 */
1521 if (s->addr) {
1522 SockAddr thisaddr = sk_extractaddr_tmp(
1523 s->addr, &s->step);
1524 plug_log(s->plug, PLUGLOG_CONNECT_FAILED, &thisaddr, s->port,
1525 winsock_error_string(err), err);
1526 while (err && s->addr && sk_nextaddr(s->addr, &s->step)) {
1527 err = try_connect(s);
1528 }
1529 }
1530 if (err != 0)
1531 plug_closing(s->plug, winsock_error_string(err), err, 0);
1532 return;
1533 }
1534
1535 noise_ultralight(NOISE_SOURCE_IOID, wParam);
1536
1537 switch (WSAGETSELECTEVENT(lParam)) {
1538 case FD_CONNECT:
1539 s->connected = true;
1540 s->writable = true;
1541
1542 /*
1543 * Once a socket is connected, we can stop falling back
1544 * through the candidate addresses to connect to. But first,
1545 * let the plug know we were successful.
1546 */
1547 if (s->addr) {
1548 SockAddr thisaddr = sk_extractaddr_tmp(
1549 s->addr, &s->step);
1550 plug_log(s->plug, PLUGLOG_CONNECT_SUCCESS,
1551 &thisaddr, s->port, NULL, 0);
1552
1553 sk_addr_free(s->addr);
1554 s->addr = NULL;
1555 }
1556 break;
1557 case FD_READ:
1558 /* In the case the socket is still frozen, we don't even bother */
1559 if (s->frozen) {
1560 s->frozen_readable = true;
1561 break;
1562 }
1563
1564 /*
1565 * We have received data on the socket. For an oobinline
1566 * socket, this might be data _before_ an urgent pointer,
1567 * in which case we send it to the back end with type==1
1568 * (data prior to urgent).
1569 */
1570 if (s->oobinline) {
1571 u_long atmark_from_ioctl = 1;
1572 p_ioctlsocket(s->s, SIOCATMARK, &atmark_from_ioctl);
1573 /*
1574 * Avoid checking the return value from ioctlsocket(),
1575 * on the grounds that some WinSock wrappers don't
1576 * support it. If it does nothing, we get atmark==1,
1577 * which is equivalent to `no OOB pending', so the
1578 * effect will be to non-OOB-ify any OOB data.
1579 */
1580 atmark = atmark_from_ioctl;
1581 } else
1582 atmark = true;
1583
1584 ret = p_recv(s->s, buf, sizeof(buf), 0);
1585 noise_ultralight(NOISE_SOURCE_IOLEN, ret);
1586 if (ret < 0) {
1587 err = p_WSAGetLastError();
1588 if (err == WSAEWOULDBLOCK) {
1589 break;
1590 }
1591 }
1592 if (ret < 0) {
1593 plug_closing(s->plug, winsock_error_string(err), err, 0);
1594 } else if (0 == ret) {
1595 plug_closing(s->plug, NULL, 0, 0);
1596 } else {
1597 plug_receive(s->plug, atmark ? 0 : 1, buf, ret);
1598 }
1599 break;
1600 case FD_OOB:
1601 /*
1602 * This will only happen on a non-oobinline socket. It
1603 * indicates that we can immediately perform an OOB read
1604 * and get back OOB data, which we will send to the back
1605 * end with type==2 (urgent data).
1606 */
1607 ret = p_recv(s->s, buf, sizeof(buf), MSG_OOB);
1608 noise_ultralight(NOISE_SOURCE_IOLEN, ret);
1609 if (ret <= 0) {
1610 int err = p_WSAGetLastError();
1611 plug_closing(s->plug, winsock_error_string(err), err, 0);
1612 } else {
1613 plug_receive(s->plug, 2, buf, ret);
1614 }
1615 break;
1616 case FD_WRITE: {
1617 int bufsize_before, bufsize_after;
1618 s->writable = true;
1619 bufsize_before = s->sending_oob + bufchain_size(&s->output_data);
1620 try_send(s);
1621 bufsize_after = s->sending_oob + bufchain_size(&s->output_data);
1622 if (bufsize_after < bufsize_before)
1623 plug_sent(s->plug, bufsize_after);
1624 break;
1625 }
1626 case FD_CLOSE:
1627 /* Signal a close on the socket. First read any outstanding data. */
1628 do {
1629 ret = p_recv(s->s, buf, sizeof(buf), 0);
1630 if (ret < 0) {
1631 err = p_WSAGetLastError();
1632 if (err == WSAEWOULDBLOCK)
1633 break;
1634 plug_closing(s->plug, winsock_error_string(err), err, 0);
1635 } else {
1636 if (ret)
1637 plug_receive(s->plug, 0, buf, ret);
1638 else
1639 plug_closing(s->plug, NULL, 0, 0);
1640 }
1641 } while (ret > 0);
1642 return;
1643 case FD_ACCEPT: {
1644 #ifdef NO_IPV6
1645 struct sockaddr_in isa;
1646 #else
1647 struct sockaddr_storage isa;
1648 #endif
1649 int addrlen = sizeof(isa);
1650 SOCKET t; /* socket of connection */
1651 accept_ctx_t actx;
1652
1653 memset(&isa, 0, sizeof(isa));
1654 err = 0;
1655 t = p_accept(s->s,(struct sockaddr *)&isa,&addrlen);
1656 if (t == INVALID_SOCKET)
1657 {
1658 err = p_WSAGetLastError();
1659 if (err == WSATRY_AGAIN)
1660 break;
1661 }
1662
1663 actx.p = (void *)t;
1664
1665 #ifndef NO_IPV6
1666 if (isa.ss_family == AF_INET &&
1667 s->localhost_only &&
1668 !ipv4_is_local_addr(((struct sockaddr_in *)&isa)->sin_addr))
1669 #else
1670 if (s->localhost_only && !ipv4_is_local_addr(isa.sin_addr))
1671 #endif
1672 {
1673 p_closesocket(t); /* dodgy WinSock let nonlocal through */
1674 } else if (plug_accepting(s->plug, sk_net_accept, actx)) {
1675 p_closesocket(t); /* denied or error */
1676 }
1677 break;
1678 }
1679 }
1680 }
1681
1682 /*
1683 * Special error values are returned from sk_namelookup and sk_new
1684 * if there's a problem. These functions extract an error message,
1685 * or return NULL if there's no problem.
1686 */
sk_addr_error(SockAddr * addr)1687 const char *sk_addr_error(SockAddr *addr)
1688 {
1689 return addr->error;
1690 }
sk_net_socket_error(Socket * sock)1691 static const char *sk_net_socket_error(Socket *sock)
1692 {
1693 NetSocket *s = container_of(sock, NetSocket, sock);
1694 return s->error;
1695 }
1696
sk_net_peer_info(Socket * sock)1697 static SocketPeerInfo *sk_net_peer_info(Socket *sock)
1698 {
1699 NetSocket *s = container_of(sock, NetSocket, sock);
1700 #ifdef NO_IPV6
1701 struct sockaddr_in addr;
1702 #else
1703 struct sockaddr_storage addr;
1704 char buf[INET6_ADDRSTRLEN];
1705 #endif
1706 int addrlen = sizeof(addr);
1707 SocketPeerInfo *pi;
1708
1709 if (p_getpeername(s->s, (struct sockaddr *)&addr, &addrlen) < 0)
1710 return NULL;
1711
1712 pi = snew(SocketPeerInfo);
1713 pi->addressfamily = ADDRTYPE_UNSPEC;
1714 pi->addr_text = NULL;
1715 pi->port = -1;
1716 pi->log_text = NULL;
1717
1718 if (((struct sockaddr *)&addr)->sa_family == AF_INET) {
1719 pi->addressfamily = ADDRTYPE_IPV4;
1720 memcpy(pi->addr_bin.ipv4, &((struct sockaddr_in *)&addr)->sin_addr, 4);
1721 pi->port = p_ntohs(((struct sockaddr_in *)&addr)->sin_port);
1722 pi->addr_text = dupstr(
1723 p_inet_ntoa(((struct sockaddr_in *)&addr)->sin_addr));
1724 pi->log_text = dupprintf("%s:%d", pi->addr_text, pi->port);
1725
1726 #ifndef NO_IPV6
1727 } else if (((struct sockaddr *)&addr)->sa_family == AF_INET6) {
1728 pi->addressfamily = ADDRTYPE_IPV6;
1729 memcpy(pi->addr_bin.ipv6,
1730 &((struct sockaddr_in6 *)&addr)->sin6_addr, 16);
1731 pi->port = p_ntohs(((struct sockaddr_in6 *)&addr)->sin6_port);
1732 pi->addr_text = dupstr(
1733 p_inet_ntop(AF_INET6, &((struct sockaddr_in6 *)&addr)->sin6_addr,
1734 buf, sizeof(buf)));
1735 pi->log_text = dupprintf("[%s]:%d", pi->addr_text, pi->port);
1736
1737 #endif
1738 } else {
1739 sfree(pi);
1740 return NULL;
1741 }
1742
1743 return pi;
1744 }
1745
sk_net_set_frozen(Socket * sock,bool is_frozen)1746 static void sk_net_set_frozen(Socket *sock, bool is_frozen)
1747 {
1748 NetSocket *s = container_of(sock, NetSocket, sock);
1749 if (s->frozen == is_frozen)
1750 return;
1751 s->frozen = is_frozen;
1752 if (!is_frozen) {
1753 do_select(s->s, true);
1754 if (s->frozen_readable) {
1755 char c;
1756 p_recv(s->s, &c, 1, MSG_PEEK);
1757 }
1758 }
1759 s->frozen_readable = false;
1760 }
1761
socket_reselect_all(void)1762 void socket_reselect_all(void)
1763 {
1764 NetSocket *s;
1765 int i;
1766
1767 for (i = 0; (s = index234(sktree, i)) != NULL; i++) {
1768 if (!s->frozen)
1769 do_select(s->s, true);
1770 }
1771 }
1772
1773 /*
1774 * For Plink: enumerate all sockets currently active.
1775 */
first_socket(int * state)1776 SOCKET first_socket(int *state)
1777 {
1778 NetSocket *s;
1779 *state = 0;
1780 s = index234(sktree, (*state)++);
1781 return s ? s->s : INVALID_SOCKET;
1782 }
1783
next_socket(int * state)1784 SOCKET next_socket(int *state)
1785 {
1786 NetSocket *s = index234(sktree, (*state)++);
1787 return s ? s->s : INVALID_SOCKET;
1788 }
1789
socket_writable(SOCKET skt)1790 bool socket_writable(SOCKET skt)
1791 {
1792 NetSocket *s = find234(sktree, (void *)skt, cmpforsearch);
1793
1794 if (s)
1795 return bufchain_size(&s->output_data) > 0;
1796 else
1797 return false;
1798 }
1799
net_service_lookup(char * service)1800 int net_service_lookup(char *service)
1801 {
1802 struct servent *se;
1803 se = p_getservbyname(service, NULL);
1804 if (se != NULL)
1805 return p_ntohs(se->s_port);
1806 else
1807 return 0;
1808 }
1809
get_hostname(void)1810 char *get_hostname(void)
1811 {
1812 char hostbuf[256]; /* MSDN docs for gethostname() promise this is enough */
1813 if (p_gethostname(hostbuf, sizeof(hostbuf)) < 0)
1814 return NULL;
1815 return dupstr(hostbuf);
1816 }
1817
platform_get_x11_unix_address(const char * display,int displaynum)1818 SockAddr *platform_get_x11_unix_address(const char *display, int displaynum)
1819 {
1820 SockAddr *ret = snew(SockAddr);
1821 memset(ret, 0, sizeof(SockAddr));
1822 ret->error = "unix sockets not supported on this platform";
1823 ret->refcount = 1;
1824 return ret;
1825 }
1826