]> sjero.net Git - wget/blob - src/connect.c
[svn] Various IPv6 fixes.
[wget] / src / connect.c
1 /* Establishing and handling network connections.
2    Copyright (C) 1995, 1996, 1997, 2001, 2002 Free Software Foundation, Inc.
3
4 This file is part of GNU Wget.
5
6 GNU Wget is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 GNU Wget is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with Wget; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
19
20 #include <config.h>
21
22 #include <stdio.h>
23 #include <sys/types.h>
24 #ifdef HAVE_UNISTD_H
25 # include <unistd.h>
26 #endif
27 #include <assert.h>
28
29 #ifdef WINDOWS
30 # include <winsock.h>
31 #else
32 # include <sys/socket.h>
33 # include <netdb.h>
34 # include <netinet/in.h>
35 #ifndef __BEOS__
36 # include <arpa/inet.h>
37 #endif
38 #endif /* WINDOWS */
39
40 #include <errno.h>
41 #ifdef HAVE_STRING_H
42 # include <string.h>
43 #else
44 # include <strings.h>
45 #endif /* HAVE_STRING_H */
46 #ifdef HAVE_SYS_SELECT_H
47 # include <sys/select.h>
48 #endif /* HAVE_SYS_SELECT_H */
49
50 #include "wget.h"
51 #include "host.h"
52 #include "connect.h"
53
54 #ifndef errno
55 extern int errno;
56 #endif
57
58 /* Variables shared by bindport and acceptport: */
59 static int msock = -1;
60 static struct sockaddr *addr;
61
62 static ip_address bind_address;
63 static int bind_address_resolved;
64
65 static void
66 resolve_bind_address (void)
67 {
68   struct address_list *al;
69
70   if (bind_address_resolved || opt.bind_address == NULL)
71     /* Nothing to do. */
72     return;
73
74   al = lookup_host (opt.bind_address, 1);
75   if (!al)
76     {
77       logprintf (LOG_NOTQUIET,
78                  _("Unable to convert `%s' to a bind address.  Reverting to ANY.\n"),
79                  opt.bind_address);
80       return;
81     }
82
83   address_list_copy_one (al, 0, &bind_address);
84   address_list_release (al);
85   bind_address_resolved = 1;
86 }
87
88 /* A kludge, but still better than passing the host name all the way
89    to connect_to_one.  */
90 static const char *connection_host_name;
91
92 void
93 set_connection_host_name (const char *host)
94 {
95   if (host)
96     assert (connection_host_name == NULL);
97   else
98     assert (connection_host_name != NULL);
99
100   connection_host_name = host;
101 }
102
103 /* Connect to a remote host whose address has been resolved. */
104 int
105 connect_to_one (ip_address *addr, unsigned short port, int silent)
106 {
107   wget_sockaddr sa;
108   int sock, save_errno;
109
110   /* Set port and protocol */
111   wget_sockaddr_set_address (&sa, ip_default_family, port, addr);
112
113   if (!silent)
114     {
115       char *pretty_addr = pretty_print_address (addr);
116       if (connection_host_name
117           && 0 != strcmp (connection_host_name, pretty_addr))
118         logprintf (LOG_VERBOSE, _("Connecting to %s[%s]:%hu... "),
119                    connection_host_name, pretty_addr, port);
120       else
121         logprintf (LOG_VERBOSE, _("Connecting to %s:%hu... "),
122                    pretty_addr, port);
123     }
124
125   /* Make an internet socket, stream type.  */
126   sock = socket (ip_default_family, SOCK_STREAM, 0);
127   if (sock < 0)
128     goto out;
129
130   resolve_bind_address ();
131   if (bind_address_resolved)
132     {
133       /* Bind the client side to the requested address. */
134       wget_sockaddr bsa;
135       wget_sockaddr_set_address (&bsa, ip_default_family, 0, &bind_address);
136       if (bind (sock, &bsa.sa, sockaddr_len ()))
137         {
138           close (sock);
139           sock = -1;
140           goto out;
141         }
142     }
143
144   /* Connect the socket to the remote host.  */
145   if (connect (sock, &sa.sa, sockaddr_len ()) < 0)
146     {
147       close (sock);
148       sock = -1;
149       goto out;
150     }
151
152  out:
153   if (sock >= 0)
154     {
155       /* Success. */
156       if (!silent)
157         logprintf (LOG_VERBOSE, _("connected.\n"));
158       DEBUGP (("Created socket %d.\n", sock));
159     }
160   else
161     {
162       save_errno = errno;
163       if (!silent)
164         logprintf (LOG_VERBOSE, "failed: %s.\n", strerror (errno));
165       errno = save_errno;
166     }
167
168   return sock;
169 }
170
171 /* Connect to a remote host whose address has been resolved. */
172 int
173 connect_to_many (struct address_list *al, unsigned short port, int silent)
174 {
175   int i, start, end;
176
177   address_list_get_bounds (al, &start, &end);
178   for (i = start; i < end; i++)
179     {
180       ip_address addr;
181       int sock;
182       address_list_copy_one (al, i, &addr);
183
184       sock = connect_to_one (&addr, port, silent);
185       if (sock >= 0)
186         /* Success. */
187         return sock;
188
189       address_list_set_faulty (al, i);
190
191       /* The attempt to connect has failed.  Continue with the loop
192          and try next address. */
193     }
194
195   return -1;
196 }
197
198 int
199 test_socket_open (int sock)
200 {
201 #ifdef HAVE_SELECT
202   fd_set check_set;
203   struct timeval to;
204
205   /* Check if we still have a valid (non-EOF) connection.  From Andrew
206    * Maholski's code in the Unix Socket FAQ.  */
207
208   FD_ZERO (&check_set);
209   FD_SET (sock, &check_set);
210
211   /* Wait one microsecond */
212   to.tv_sec = 0;
213   to.tv_usec = 1;
214
215   /* If we get a timeout, then that means still connected */
216   if (select (sock + 1, &check_set, NULL, NULL, &to) == 0)
217     {
218       /* Connection is valid (not EOF), so continue */
219       return 1;
220     }
221   else
222     return 0;
223 #else
224   /* Without select, it's hard to know for sure. */
225   return 1;
226 #endif
227 }
228
229 /* Bind the local port PORT.  This does all the necessary work, which
230    is creating a socket, setting SO_REUSEADDR option on it, then
231    calling bind() and listen().  If *PORT is 0, a random port is
232    chosen by the system, and its value is stored to *PORT.  The
233    internal variable MPORT is set to the value of the ensuing master
234    socket.  Call acceptport() to block for and accept a connection.  */
235 uerr_t
236 bindport (unsigned short *port, int family)
237 {
238   int optval = 1;
239   wget_sockaddr srv;
240   memset (&srv, 0, sizeof (wget_sockaddr));
241
242   msock = -1;
243
244   if ((msock = socket (family, SOCK_STREAM, 0)) < 0)
245     return CONSOCKERR;
246   if (setsockopt (msock, SOL_SOCKET, SO_REUSEADDR,
247                   (char *)&optval, sizeof (optval)) < 0)
248     return CONSOCKERR;
249
250   resolve_bind_address ();
251   wget_sockaddr_set_address (&srv, ip_default_family, htons (*port),
252                              bind_address_resolved ? &bind_address : NULL);
253   if (bind (msock, &srv.sa, sockaddr_len ()) < 0)
254     {
255       CLOSE (msock);
256       msock = -1;
257       return BINDERR;
258     }
259   DEBUGP (("Master socket fd %d bound.\n", msock));
260   if (!*port)
261     {
262       /* #### addrlen should be a 32-bit type, which int is not
263          guaranteed to be.  Oh, and don't try to make it a size_t,
264          because that can be 64-bit.  */
265       int sa_len = sockaddr_len ();
266       if (getsockname (msock, &srv.sa, &sa_len) < 0)
267         {
268           CLOSE (msock);
269           msock = -1;
270           return CONPORTERR;
271         }
272       *port = wget_sockaddr_get_port (&srv);
273       DEBUGP (("using port %i.\n", *port));
274     }
275   if (listen (msock, 1) < 0)
276     {
277       CLOSE (msock);
278       msock = -1;
279       return LISTENERR;
280     }
281   return BINDOK;
282 }
283
284 #ifdef HAVE_SELECT
285 /* Wait for file descriptor FD to be readable, MAXTIME being the
286    timeout in seconds.  If WRITEP is non-zero, checks for FD being
287    writable instead.
288
289    Returns 1 if FD is accessible, 0 for timeout and -1 for error in
290    select().  */
291 int
292 select_fd (int fd, int maxtime, int writep)
293 {
294   fd_set fds, exceptfds;
295   struct timeval timeout;
296
297   FD_ZERO (&fds);
298   FD_SET (fd, &fds);
299   FD_ZERO (&exceptfds);
300   FD_SET (fd, &exceptfds);
301   timeout.tv_sec = maxtime;
302   timeout.tv_usec = 0;
303   /* HPUX reportedly warns here.  What is the correct incantation?  */
304   return select (fd + 1, writep ? NULL : &fds, writep ? &fds : NULL,
305                  &exceptfds, &timeout);
306 }
307 #endif /* HAVE_SELECT */
308
309 /* Call accept() on MSOCK and store the result to *SOCK.  This assumes
310    that bindport() has been used to initialize MSOCK to a correct
311    value.  It blocks the caller until a connection is established.  If
312    no connection is established for OPT.TIMEOUT seconds, the function
313    exits with an error status.  */
314 uerr_t
315 acceptport (int *sock)
316 {
317   int addrlen = sockaddr_len ();
318
319 #ifdef HAVE_SELECT
320   if (select_fd (msock, opt.timeout, 0) <= 0)
321     return ACCEPTERR;
322 #endif
323   if ((*sock = accept (msock, addr, &addrlen)) < 0)
324     return ACCEPTERR;
325   DEBUGP (("Created socket fd %d.\n", *sock));
326   return ACCEPTOK;
327 }
328
329 /* Close SOCK, as well as the most recently remembered MSOCK, created
330    via bindport().  If SOCK is -1, close MSOCK only.  */
331 void
332 closeport (int sock)
333 {
334   /*shutdown (sock, 2);*/
335   if (sock != -1)
336     CLOSE (sock);
337   if (msock != -1)
338     CLOSE (msock);
339   msock = -1;
340 }
341
342 /* Return the local IP address associated with the connection on FD.  */
343
344 int
345 conaddr (int fd, ip_address *ip)
346 {
347   wget_sockaddr mysrv;
348
349   /* see bindport() for discussion of using `int' here. */
350   int addrlen = sizeof (mysrv); 
351
352   if (getsockname (fd, &mysrv.sa, (int *)&addrlen) < 0)
353     return 0;
354
355   switch (mysrv.sa.sa_family)
356     {
357 #ifdef INET6
358     case AF_INET6:
359       memcpy (ip, &mysrv.sin6.sin6_addr, 16);
360       return 1;
361 #endif
362     case AF_INET:
363       map_ipv4_to_ip ((ip4_address *)&mysrv.sin.sin_addr, ip);
364       return 1;
365     default:
366       abort ();
367     }
368   return 0;
369 }
370
371 /* Read at most LEN bytes from FD, storing them to BUF.  This is
372    virtually the same as read(), but takes care of EINTR braindamage
373    and uses select() to timeout the stale connections (a connection is
374    stale if more than OPT.TIMEOUT time is spent in select() or
375    read()).  */
376 int
377 iread (int fd, char *buf, int len)
378 {
379   int res;
380
381   do
382     {
383 #ifdef HAVE_SELECT
384       if (opt.timeout)
385         {
386           do
387             {
388               res = select_fd (fd, opt.timeout, 0);
389             }
390           while (res == -1 && errno == EINTR);
391           if (res <= 0)
392             {
393               /* Set errno to ETIMEDOUT on timeout.  */
394               if (res == 0)
395                 /* #### Potentially evil!  */
396                 errno = ETIMEDOUT;
397               return -1;
398             }
399         }
400 #endif
401       res = READ (fd, buf, len);
402     }
403   while (res == -1 && errno == EINTR);
404
405   return res;
406 }
407
408 /* Write LEN bytes from BUF to FD.  This is similar to iread(), but
409    doesn't bother with select().  Unlike iread(), it makes sure that
410    all of BUF is actually written to FD, so callers needn't bother
411    with checking that the return value equals to LEN.  Instead, you
412    should simply check for -1.  */
413 int
414 iwrite (int fd, char *buf, int len)
415 {
416   int res = 0;
417
418   /* `write' may write less than LEN bytes, thus the outward loop
419      keeps trying it until all was written, or an error occurred.  The
420      inner loop is reserved for the usual EINTR f*kage, and the
421      innermost loop deals with the same during select().  */
422   while (len > 0)
423     {
424       do
425         {
426 #ifdef HAVE_SELECT
427           if (opt.timeout)
428             {
429               do
430                 {
431                   res = select_fd (fd, opt.timeout, 1);
432                 }
433               while (res == -1 && errno == EINTR);
434               if (res <= 0)
435                 {
436                   /* Set errno to ETIMEDOUT on timeout.  */
437                   if (res == 0)
438                     /* #### Potentially evil!  */
439                     errno = ETIMEDOUT;
440                   return -1;
441                 }
442             }
443 #endif
444           res = WRITE (fd, buf, len);
445         }
446       while (res == -1 && errno == EINTR);
447       if (res <= 0)
448         break;
449       buf += res;
450       len -= res;
451     }
452   return res;
453 }