]> sjero.net Git - wget/blob - src/retr.c
772d922ce4b48858e5f4a1f63ceb27893ddf9f82
[wget] / src / retr.c
1 /* File retrieval.
2    Copyright (C) 1995, 1996, 1997, 1998, 2000, 2001 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 <stdlib.h>
24 #include <sys/types.h>
25 #ifdef HAVE_UNISTD_H
26 # include <unistd.h>
27 #endif /* HAVE_UNISTD_H */
28 #include <errno.h>
29 #ifdef HAVE_STRING_H
30 # include <string.h>
31 #else
32 # include <strings.h>
33 #endif /* HAVE_STRING_H */
34 #include <assert.h>
35
36 #include "wget.h"
37 #include "utils.h"
38 #include "retr.h"
39 #include "progress.h"
40 #include "url.h"
41 #include "recur.h"
42 #include "ftp.h"
43 #include "host.h"
44 #include "connect.h"
45 #include "hash.h"
46
47 #ifdef HAVE_SSL
48 # include "gen_sslfunc.h"       /* for ssl_iread */
49 #endif
50
51 #ifndef errno
52 extern int errno;
53 #endif
54
55 /* See the comment in gethttp() why this is needed. */
56 int global_download_count;
57
58 \f
59 static struct {
60   long bytes;
61   long dltime;
62 } limit_data;
63
64 static void
65 limit_bandwidth_reset (void)
66 {
67   limit_data.bytes  = 0;
68   limit_data.dltime = 0;
69 }
70
71 /* Limit the bandwidth by pausing the download for an amount of time.
72    BYTES is the number of bytes received from the network, DELTA is
73    how long it took to receive them, DLTIME the current download time,
74    TIMER the timer, and ADJUSTMENT the previous.  */
75
76 static void
77 limit_bandwidth (long bytes, long delta)
78 {
79   long expected;
80
81   limit_data.bytes += bytes;
82   limit_data.dltime += delta;
83
84   expected = (long)(1000.0 * limit_data.bytes / opt.limit_rate);
85
86   if (expected > limit_data.dltime)
87     {
88       long slp = expected - limit_data.dltime;
89       if (slp < 200)
90         {
91           DEBUGP (("deferring a %ld ms sleep (%ld/%ld) until later.\n",
92                    slp, limit_data.bytes, limit_data.dltime));
93           return;
94         }
95       DEBUGP (("sleeping %ld ms\n", slp));
96       usleep (1000 * slp);
97     }
98
99   limit_data.bytes = 0;
100   limit_data.dltime = 0;
101 }
102
103 #define MIN(i, j) ((i) <= (j) ? (i) : (j))
104
105 /* Reads the contents of file descriptor FD, until it is closed, or a
106    read error occurs.  The data is read in 8K chunks, and stored to
107    stream fp, which should have been open for writing.  If BUF is
108    non-NULL and its file descriptor is equal to FD, flush RBUF first.
109    This function will *not* use the rbuf_* functions!
110
111    The EXPECTED argument is passed to show_progress() unchanged, but
112    otherwise ignored.
113
114    If opt.verbose is set, the progress is also shown.  RESTVAL
115    represents a value from which to start downloading (which will be
116    shown accordingly).  If RESTVAL is non-zero, the stream should have
117    been open for appending.
118
119    The function exits and returns codes of 0, -1 and -2 if the
120    connection was closed, there was a read error, or if it could not
121    write to the output stream, respectively.
122
123    IMPORTANT: The function flushes the contents of the buffer in
124    rbuf_flush() before actually reading from fd.  If you wish to read
125    from fd immediately, flush or discard the buffer.  */
126 int
127 get_contents (int fd, FILE *fp, long *len, long restval, long expected,
128               struct rbuf *rbuf, int use_expected, long *elapsed)
129 {
130   int res = 0;
131   static char c[8192];
132   void *progress = NULL;
133   struct wget_timer *timer = wtimer_allocate ();
134   long dltime = 0, last_dltime = 0;
135
136   *len = restval;
137
138   if (opt.verbose)
139     progress = progress_create (restval, expected);
140
141   if (rbuf && RBUF_FD (rbuf) == fd)
142     {
143       int sz = 0;
144       while ((res = rbuf_flush (rbuf, c, sizeof (c))) != 0)
145         {
146           fwrite (c, sizeof (char), res, fp);
147           *len += res;
148           sz += res;
149         }
150       if (sz)
151         fflush (fp);
152       if (ferror (fp))
153         {
154           res = -2;
155           goto out;
156         }
157       if (opt.verbose)
158         progress_update (progress, sz, 0);
159     }
160
161   if (opt.limit_rate)
162     limit_bandwidth_reset ();
163   wtimer_reset (timer);
164
165   /* Read from fd while there is available data.
166
167      Normally, if expected is 0, it means that it is not known how
168      much data is expected.  However, if use_expected is specified,
169      then expected being zero means exactly that.  */
170   while (!use_expected || (*len < expected))
171     {
172       int amount_to_read = (use_expected
173                             ? MIN (expected - *len, sizeof (c))
174                             : sizeof (c));
175 #ifdef HAVE_SSL
176       if (rbuf->ssl!=NULL)
177         res = ssl_iread (rbuf->ssl, c, amount_to_read);
178       else
179 #endif /* HAVE_SSL */
180         res = iread (fd, c, amount_to_read);
181
182       if (res > 0)
183         {
184           fwrite (c, sizeof (char), res, fp);
185           /* Always flush the contents of the network packet.  This
186              should not be adverse to performance, as the network
187              packets typically won't be too tiny anyway.  */
188           fflush (fp);
189           if (ferror (fp))
190             {
191               res = -2;
192               goto out;
193             }
194
195           /* If bandwidth is not limited, one call to wtimer_elapsed
196              is sufficient.  */
197           dltime = wtimer_elapsed (timer);
198           if (opt.limit_rate)
199             {
200               limit_bandwidth (res, dltime - last_dltime);
201               dltime = wtimer_elapsed (timer);
202               last_dltime = dltime;
203             }
204
205           if (opt.verbose)
206             progress_update (progress, res, dltime);
207           *len += res;
208         }
209       else
210         break;
211     }
212   if (res < -1)
213     res = -1;
214
215  out:
216   if (opt.verbose)
217     progress_finish (progress, dltime);
218   if (elapsed)
219     *elapsed = dltime;
220   wtimer_delete (timer);
221
222   return res;
223 }
224 \f
225 /* Return a printed representation of the download rate, as
226    appropriate for the speed.  If PAD is non-zero, strings will be
227    padded to the width of 7 characters (xxxx.xx).  */
228 char *
229 retr_rate (long bytes, long msecs, int pad)
230 {
231   static char res[20];
232   static char *rate_names[] = {"B/s", "KB/s", "MB/s", "GB/s" };
233   int units = 0;
234
235   double dlrate = calc_rate (bytes, msecs, &units);
236   sprintf (res, pad ? "%7.2f %s" : "%.2f %s", dlrate, rate_names[units]);
237
238   return res;
239 }
240
241 /* Calculate the download rate and trim it as appropriate for the
242    speed.  Appropriate means that if rate is greater than 1K/s,
243    kilobytes are used, and if rate is greater than 1MB/s, megabytes
244    are used.
245
246    UNITS is zero for B/s, one for KB/s, two for MB/s, and three for
247    GB/s.  */
248 double
249 calc_rate (long bytes, long msecs, int *units)
250 {
251   double dlrate;
252
253   assert (msecs >= 0);
254   assert (bytes >= 0);
255
256   if (msecs == 0)
257     /* If elapsed time is 0, it means we're under the granularity of
258        the timer.  This often happens on systems that use time() for
259        the timer.  */
260     msecs = wtimer_granularity ();
261
262   dlrate = (double)1000 * bytes / msecs;
263   if (dlrate < 1024.0)
264     *units = 0;
265   else if (dlrate < 1024.0 * 1024.0)
266     *units = 1, dlrate /= 1024.0;
267   else if (dlrate < 1024.0 * 1024.0 * 1024.0)
268     *units = 2, dlrate /= (1024.0 * 1024.0);
269   else
270     /* Maybe someone will need this one day.  More realistically, it
271        will get tickled by buggy timers. */
272     *units = 3, dlrate /= (1024.0 * 1024.0 * 1024.0);
273
274   return dlrate;
275 }
276 \f
277 /* Maximum number of allowed redirections.  20 was chosen as a
278    "reasonable" value, which is low enough to not cause havoc, yet
279    high enough to guarantee that normal retrievals will not be hurt by
280    the check.  */
281
282 #define MAX_REDIRECTIONS 20
283
284 /* Retrieve the given URL.  Decides which loop to call -- HTTP, FTP,
285    FTP, proxy, etc.  */
286
287 uerr_t
288 retrieve_url (const char *origurl, char **file, char **newloc,
289               const char *refurl, int *dt)
290 {
291   uerr_t result;
292   char *url;
293   int location_changed, dummy;
294   char *mynewloc, *proxy;
295   struct url *u, *proxy_url;
296   int up_error_code;            /* url parse error code */
297   char *local_file;
298   int redirection_count = 0;
299
300   /* If dt is NULL, just ignore it.  */
301   if (!dt)
302     dt = &dummy;
303   url = xstrdup (origurl);
304   if (newloc)
305     *newloc = NULL;
306   if (file)
307     *file = NULL;
308
309   u = url_parse (url, &up_error_code);
310   if (!u)
311     {
312       logprintf (LOG_NOTQUIET, "%s: %s.\n", url, url_error (up_error_code));
313       xfree (url);
314       return URLERROR;
315     }
316
317   if (!refurl)
318     refurl = opt.referer;
319
320  redirected:
321
322   result = NOCONERROR;
323   mynewloc = NULL;
324   local_file = NULL;
325   proxy_url = NULL;
326
327   proxy = getproxy (u);
328   if (proxy)
329     {
330       /* Parse the proxy URL.  */
331       proxy_url = url_parse (proxy, &up_error_code);
332       if (!proxy_url)
333         {
334           logprintf (LOG_NOTQUIET, _("Error parsing proxy URL %s: %s.\n"),
335                      proxy, url_error (up_error_code));
336           xfree (url);
337           return PROXERR;
338         }
339       if (proxy_url->scheme != SCHEME_HTTP && proxy_url->scheme != u->scheme)
340         {
341           logprintf (LOG_NOTQUIET, _("Error in proxy URL %s: Must be HTTP.\n"), proxy);
342           url_free (proxy_url);
343           xfree (url);
344           return PROXERR;
345         }
346     }
347
348   if (u->scheme == SCHEME_HTTP
349 #ifdef HAVE_SSL
350       || u->scheme == SCHEME_HTTPS
351 #endif
352       || (proxy_url && proxy_url->scheme == SCHEME_HTTP))
353     {
354       result = http_loop (u, &mynewloc, &local_file, refurl, dt, proxy_url);
355     }
356   else if (u->scheme == SCHEME_FTP)
357     {
358       /* If this is a redirection, we must not allow recursive FTP
359          retrieval, so we save recursion to oldrec, and restore it
360          later.  */
361       int oldrec = opt.recursive;
362       if (redirection_count)
363         opt.recursive = 0;
364       result = ftp_loop (u, dt, proxy_url);
365       opt.recursive = oldrec;
366
367       /* There is a possibility of having HTTP being redirected to
368          FTP.  In these cases we must decide whether the text is HTML
369          according to the suffix.  The HTML suffixes are `.html',
370          `.htm' and a few others, case-insensitive.  */
371       if (redirection_count && local_file && u->scheme == SCHEME_FTP)
372         {
373           if (has_html_suffix_p (local_file))
374             *dt |= TEXTHTML;
375         }
376     }
377
378   if (proxy_url)
379     {
380       url_free (proxy_url);
381       proxy_url = NULL;
382     }
383
384   location_changed = (result == NEWLOCATION);
385   if (location_changed)
386     {
387       char *construced_newloc;
388       struct url *newloc_parsed;
389
390       assert (mynewloc != NULL);
391
392       if (local_file)
393         xfree (local_file);
394
395       /* The HTTP specs only allow absolute URLs to appear in
396          redirects, but a ton of boneheaded webservers and CGIs out
397          there break the rules and use relative URLs, and popular
398          browsers are lenient about this, so wget should be too. */
399       construced_newloc = uri_merge (url, mynewloc);
400       xfree (mynewloc);
401       mynewloc = construced_newloc;
402
403       /* Now, see if this new location makes sense. */
404       newloc_parsed = url_parse (mynewloc, &up_error_code);
405       if (!newloc_parsed)
406         {
407           logprintf (LOG_NOTQUIET, "%s: %s.\n", mynewloc,
408                      url_error (up_error_code));
409           url_free (u);
410           xfree (url);
411           xfree (mynewloc);
412           return result;
413         }
414
415       /* Now mynewloc will become newloc_parsed->url, because if the
416          Location contained relative paths like .././something, we
417          don't want that propagating as url.  */
418       xfree (mynewloc);
419       mynewloc = xstrdup (newloc_parsed->url);
420
421       /* Check for max. number of redirections.  */
422       if (++redirection_count > MAX_REDIRECTIONS)
423         {
424           logprintf (LOG_NOTQUIET, _("%d redirections exceeded.\n"),
425                      MAX_REDIRECTIONS);
426           url_free (newloc_parsed);
427           url_free (u);
428           xfree (url);
429           xfree (mynewloc);
430           return WRONGCODE;
431         }
432
433       xfree (url);
434       url = mynewloc;
435       url_free (u);
436       u = newloc_parsed;
437       goto redirected;
438     }
439
440   if (local_file)
441     {
442       if (*dt & RETROKF)
443         {
444           register_download (u->url, local_file);
445           if (redirection_count && 0 != strcmp (origurl, u->url))
446             register_redirection (origurl, u->url);
447           if (*dt & TEXTHTML)
448             register_html (u->url, local_file);
449         }
450     }
451
452   if (file)
453     *file = local_file ? local_file : NULL;
454   else
455     FREE_MAYBE (local_file);
456
457   url_free (u);
458
459   if (redirection_count)
460     {
461       if (newloc)
462         *newloc = url;
463       else
464         xfree (url);
465     }
466   else
467     {
468       if (newloc)
469         *newloc = NULL;
470       xfree (url);
471     }
472
473   ++global_download_count;
474
475   return result;
476 }
477
478 /* Find the URLs in the file and call retrieve_url() for each of
479    them.  If HTML is non-zero, treat the file as HTML, and construct
480    the URLs accordingly.
481
482    If opt.recursive is set, call recursive_retrieve() for each file.  */
483 uerr_t
484 retrieve_from_file (const char *file, int html, int *count)
485 {
486   uerr_t status;
487   struct urlpos *url_list, *cur_url;
488
489   url_list = (html ? get_urls_html (file, NULL, NULL)
490               : get_urls_file (file));
491   status = RETROK;             /* Suppose everything is OK.  */
492   *count = 0;                  /* Reset the URL count.  */
493
494   for (cur_url = url_list; cur_url; cur_url = cur_url->next, ++*count)
495     {
496       char *filename = NULL, *new_file = NULL;
497       int dt;
498
499       if (cur_url->ignore_when_downloading)
500         continue;
501
502       if (downloaded_exceeds_quota ())
503         {
504           status = QUOTEXC;
505           break;
506         }
507       if (opt.recursive && cur_url->url->scheme != SCHEME_FTP)
508         status = retrieve_tree (cur_url->url->url);
509       else
510         status = retrieve_url (cur_url->url->url, &filename, &new_file, NULL, &dt);
511
512       if (filename && opt.delete_after && file_exists_p (filename))
513         {
514           DEBUGP (("Removing file due to --delete-after in"
515                    " retrieve_from_file():\n"));
516           logprintf (LOG_VERBOSE, _("Removing %s.\n"), filename);
517           if (unlink (filename))
518             logprintf (LOG_NOTQUIET, "unlink: %s\n", strerror (errno));
519           dt &= ~RETROKF;
520         }
521
522       FREE_MAYBE (new_file);
523       FREE_MAYBE (filename);
524     }
525
526   /* Free the linked list of URL-s.  */
527   free_urlpos (url_list);
528
529   return status;
530 }
531
532 /* Print `giving up', or `retrying', depending on the impending
533    action.  N1 and N2 are the attempt number and the attempt limit.  */
534 void
535 printwhat (int n1, int n2)
536 {
537   logputs (LOG_VERBOSE, (n1 == n2) ? _("Giving up.\n\n") : _("Retrying.\n\n"));
538 }
539
540 /* Increment opt.downloaded by BY_HOW_MUCH.  If an overflow occurs,
541    set opt.downloaded_overflow to 1. */
542 void
543 downloaded_increase (unsigned long by_how_much)
544 {
545   VERY_LONG_TYPE old;
546   if (opt.downloaded_overflow)
547     return;
548   old = opt.downloaded;
549   opt.downloaded += by_how_much;
550   if (opt.downloaded < old)     /* carry flag, where are you when I
551                                    need you? */
552     {
553       /* Overflow. */
554       opt.downloaded_overflow = 1;
555       opt.downloaded = ~((VERY_LONG_TYPE)0);
556     }
557 }
558
559 /* Return non-zero if the downloaded amount of bytes exceeds the
560    desired quota.  If quota is not set or if the amount overflowed, 0
561    is returned. */
562 int
563 downloaded_exceeds_quota (void)
564 {
565   if (!opt.quota)
566     return 0;
567   if (opt.downloaded_overflow)
568     /* We don't really know.  (Wildly) assume not. */
569     return 0;
570
571   return opt.downloaded > opt.quota;
572 }
573
574 /* If opt.wait or opt.waitretry are specified, and if certain
575    conditions are met, sleep the appropriate number of seconds.  See
576    the documentation of --wait and --waitretry for more information.
577
578    COUNT is the count of current retrieval, beginning with 1. */
579
580 void
581 sleep_between_retrievals (int count)
582 {
583   static int first_retrieval = 1;
584
585   if (first_retrieval)
586     {
587       /* Don't sleep before the very first retrieval. */
588       first_retrieval = 0;
589       return;
590     }
591
592   if (opt.waitretry && count > 1)
593     {
594       /* If opt.waitretry is specified and this is a retry, wait for
595          COUNT-1 number of seconds, or for opt.waitretry seconds.  */
596       if (count <= opt.waitretry)
597         sleep (count - 1);
598       else
599         sleep (opt.waitretry);
600     }
601   else if (opt.wait)
602     {
603       if (!opt.random_wait || count > 1)
604         /* If random-wait is not specified, or if we are sleeping
605            between retries of the same download, sleep the fixed
606            interval.  */
607         sleep (opt.wait);
608       else
609         {
610           /* Sleep a random amount of time averaging in opt.wait
611              seconds.  The sleeping amount ranges from 0 to
612              opt.wait*2, inclusive.  */
613           int waitsecs = random_number (opt.wait * 2 + 1);
614
615           DEBUGP (("sleep_between_retrievals: norm=%ld,fuzz=%ld,sleep=%d\n",
616                    opt.wait, waitsecs - opt.wait, waitsecs));
617
618           if (waitsecs)
619             sleep (waitsecs);
620         }
621     }
622 }