#include "netrc.h"
#include "cookies.h" /* for cookie_jar_delete */
#include "progress.h"
+#include "recur.h" /* for INFINITE_RECURSION */
#ifndef errno
extern int errno;
CMD_DECLARE (cmd_spec_timeout);
CMD_DECLARE (cmd_spec_useragent);
-/* List of recognized commands, each consisting of name, closure and function.
- When adding a new command, simply add it to the list, but be sure to keep the
- list sorted alphabetically, as findcmd() depends on it. Also, be sure to add
- any entries that allocate memory (e.g. cmd_string and cmd_vector guys) to the
+/* List of recognized commands, each consisting of name, closure and
+ function. When adding a new command, simply add it to the list,
+ but be sure to keep the list sorted alphabetically, as
+ command_by_name depends on it. Also, be sure to add any entries
+ that allocate memory (e.g. cmd_string and cmd_vector guys) to the
cleanup() function below. */
+
static struct {
char *name;
void *closure;
{ "ignoretags", &opt.ignore_tags, cmd_vector },
{ "includedirectories", &opt.includes, cmd_directory_vector },
{ "input", &opt.input_filename, cmd_file },
+ { "keepsessioncookies", &opt.keep_session_cookies, cmd_boolean },
{ "killlonger", &opt.kill_longer, cmd_boolean },
{ "limitrate", &opt.limit_rate, cmd_bytes },
{ "loadcookies", &opt.cookies_input, cmd_file },
{ "passwd", &opt.ftp_pass, cmd_string },
{ "postdata", &opt.post_data, cmd_string },
{ "postfile", &opt.post_file_name, cmd_file },
+ { "preservepermissions", &opt.preserve_perm, cmd_boolean },
{ "progress", &opt.progress_type, cmd_spec_progress },
{ "proxypasswd", &opt.proxy_passwd, cmd_string },
{ "proxyuser", &opt.proxy_user, cmd_string },
{ "waitretry", &opt.waitretry, cmd_time }
};
-/* Look up COM in the commands[] array and return its index. If COM
- is not found, -1 is returned. This function uses binary search. */
+/* Look up CMDNAME in the commands[] and return its position in the
+ array. If CMDNAME is not found, return -1. */
static int
-findcmd (const char *com)
+command_by_name (const char *cmdname)
{
+ /* Use binary search for speed. Wget has ~100 commands, which
+ guarantees a worst case performance of 7 string comparisons. */
int lo = 0, hi = countof (commands) - 1;
while (lo <= hi)
{
int mid = (lo + hi) >> 1;
- int cmp = strcasecmp (com, commands[mid].name);
+ int cmp = strcasecmp (cmdname, commands[mid].name);
if (cmp < 0)
hi = mid - 1;
else if (cmp > 0)
NULL this way is technically illegal, but porting Wget to a
machine where NULL is not all-zero bit pattern will be the least
of the implementors' worries. */
- memset (&opt, 0, sizeof (opt));
+ xzero (opt);
opt.cookies = 1;
-
opt.verbose = -1;
opt.ntry = 20;
opt.reclevel = 5;
file = (char *)xmalloc (strlen (home) + 1 + strlen (".wgetrc") + 1);
sprintf (file, "%s/.wgetrc", home);
}
- FREE_MAYBE (home);
+ xfree_null (home);
#else /* WINDOWS */
/* Under Windows, "home" is (for the purposes of this function) the
directory where `wget.exe' resides, and `wget.ini' will be used
the command is valid. */
BOUNDED_TO_ALLOCA (cmdstart, cmdend, cmdcopy);
dehyphen (cmdcopy);
- ind = findcmd (cmdcopy);
+ ind = command_by_name (cmdcopy);
if (ind == -1)
return 0;
setval_internal (int comind, const char *com, const char *val)
{
assert (0 <= comind && comind < countof (commands));
+ DEBUGP (("Setting %s (%d) to %s\n", com, comind, val));
return ((*commands[comind].action) (com, val, commands[comind].closure));
}
void
setoptval (const char *com, const char *val)
{
- if (!setval_internal (findcmd (com), com, val))
+ assert (val != NULL);
+ if (!setval_internal (command_by_name (com), com, val))
exit (2);
}
{
char **pstring = (char **)closure;
- FREE_MAYBE (*pstring);
+ xfree_null (*pstring);
*pstring = xstrdup (val);
return 1;
}
{
char **pstring = (char **)closure;
- FREE_MAYBE (*pstring);
+ xfree_null (*pstring);
/* #### If VAL is empty, perhaps should set *CLOSURE to NULL. */
if (!*val)
{
/* Empty header means reset headers. */
- FREE_MAYBE (opt.user_header);
+ xfree_null (opt.user_header);
opt.user_header = NULL;
}
else
exec_name, com, val);
return 0;
}
- FREE_MAYBE (opt.progress_type);
+ xfree_null (opt.progress_type);
/* Don't call set_progress_implementation here. It will be called
in main() when it becomes clear what the log output is. */
cleanup_html_url ();
downloaded_files_free ();
host_cleanup ();
- cookie_jar_delete (wget_cookie_jar);
+ if (wget_cookie_jar)
+ cookie_jar_delete (wget_cookie_jar);
{
extern acc_t *netrc_list;
free_netrc (netrc_list);
}
- FREE_MAYBE (opt.lfilename);
- FREE_MAYBE (opt.dir_prefix);
- FREE_MAYBE (opt.input_filename);
- FREE_MAYBE (opt.output_document);
+ xfree_null (opt.lfilename);
+ xfree_null (opt.dir_prefix);
+ xfree_null (opt.input_filename);
+ xfree_null (opt.output_document);
free_vec (opt.accepts);
free_vec (opt.rejects);
free_vec (opt.excludes);
free_vec (opt.domains);
free_vec (opt.follow_tags);
free_vec (opt.ignore_tags);
- FREE_MAYBE (opt.progress_type);
+ xfree_null (opt.progress_type);
xfree (opt.ftp_acc);
- FREE_MAYBE (opt.ftp_pass);
- FREE_MAYBE (opt.ftp_proxy);
- FREE_MAYBE (opt.https_proxy);
- FREE_MAYBE (opt.http_proxy);
+ xfree_null (opt.ftp_pass);
+ xfree_null (opt.ftp_proxy);
+ xfree_null (opt.https_proxy);
+ xfree_null (opt.http_proxy);
free_vec (opt.no_proxy);
- FREE_MAYBE (opt.useragent);
- FREE_MAYBE (opt.referer);
- FREE_MAYBE (opt.http_user);
- FREE_MAYBE (opt.http_passwd);
- FREE_MAYBE (opt.user_header);
+ xfree_null (opt.useragent);
+ xfree_null (opt.referer);
+ xfree_null (opt.http_user);
+ xfree_null (opt.http_passwd);
+ xfree_null (opt.user_header);
#ifdef HAVE_SSL
- FREE_MAYBE (opt.sslcertkey);
- FREE_MAYBE (opt.sslcertfile);
+ xfree_null (opt.sslcertkey);
+ xfree_null (opt.sslcertfile);
#endif /* HAVE_SSL */
- FREE_MAYBE (opt.bind_address);
- FREE_MAYBE (opt.cookies_input);
- FREE_MAYBE (opt.cookies_output);
+ xfree_null (opt.bind_address);
+ xfree_null (opt.cookies_input);
+ xfree_null (opt.cookies_output);
#endif
}