CMD_DECLARE (cmd_boolean);
CMD_DECLARE (cmd_bytes);
+CMD_DECLARE (cmd_bytes_large);
CMD_DECLARE (cmd_directory_vector);
CMD_DECLARE (cmd_lockable_boolean);
CMD_DECLARE (cmd_number);
{ "convertlinks", &opt.convert_links, cmd_boolean },
{ "cookies", &opt.cookies, cmd_boolean },
{ "cutdirs", &opt.cut_dirs, cmd_number },
-#ifdef DEBUG
+#ifdef ENABLE_DEBUG
{ "debug", &opt.debug, cmd_boolean },
#endif
{ "deleteafter", &opt.delete_after, cmd_boolean },
{ "proxypasswd", &opt.proxy_passwd, cmd_string },
{ "proxyuser", &opt.proxy_user, cmd_string },
{ "quiet", &opt.quiet, cmd_boolean },
- { "quota", &opt.quota, cmd_bytes },
+ { "quota", &opt.quota, cmd_bytes_large },
{ "randomwait", &opt.random_wait, cmd_boolean },
{ "readtimeout", &opt.read_timeout, cmd_time },
{ "reclevel", &opt.reclevel, cmd_number_inf },
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;
/* Run command COM with value VAL. If running the command produces an
error, report the error and exit.
- This is intended to be called from main() with commands not
- provided by the user, therefore it aborts when an unknown command
- is encountered. Once the COMIND's are exported to init.h, this
- function will be changed to accept COMIND directly. */
+ This is intended to be called from main() to modify Wget's behavior
+ through command-line switches. Since COM is hard-coded in main(),
+ it is not canonicalized, and this aborts when COM is not found.
+
+ If COMIND's are exported to init.h, this function will be changed
+ to accept COMIND directly. */
void
setoptval (const char *com, const char *val)
static int simple_atof PARAMS ((const char *, const char *, double *));
-/* Parse VAL as a number and set its value to CLOSURE (which should
- point to a long int).
-
- By default, the value is assumed to be in bytes. If "K", "M", or
- "G" are appended, the value is multiplied with 1<<10, 1<<20, or
- 1<<30, respectively. Floating point values are allowed and are
- cast to integer before use. The idea is to be able to use things
- like 1.5k instead of "1536".
-
- The string "inf" is returned as 0.
-
- In case of error, 0 is returned and memory pointed to by CLOSURE
- remains unmodified. */
+/* Enginge for cmd_bytes and cmd_bytes_large: converts a string such
+ as "100k" or "2.5G" to a floating point number. */
static int
-cmd_bytes (const char *com, const char *val, void *closure)
+parse_bytes_helper (const char *val, double *result)
{
- long mult;
- double number;
+ double number, mult;
const char *end = val + strlen (val);
/* Check for "inf". */
if (0 == strcmp (val, "inf"))
{
- *(long *)closure = 0;
+ *result = 0;
return 1;
}
/* Strip trailing whitespace. */
while (val < end && ISSPACE (end[-1]))
--end;
-
if (val == end)
- {
- err:
- fprintf (stderr, _("%s: %s: Invalid byte value `%s'\n"),
- exec_name, com, val);
- return 0;
- }
+ return 0;
switch (TOLOWER (end[-1]))
{
case 'k':
- --end, mult = 1L<<10;
+ --end, mult = 1024.0;
break;
case 'm':
- --end, mult = 1L<<20;
+ --end, mult = 1048576.0;
break;
case 'g':
- --end, mult = 1L<<30;
+ --end, mult = 1073741824.0;
+ break;
+ case 't':
+ --end, mult = 1099511627776.0;
break;
default:
- /* Not a recognized suffix: assume it belongs to the number.
- (If not, atof simple_atof will raise an error.) */
+ /* Not a recognized suffix: assume it's a digit. (If not,
+ simple_atof will raise an error.) */
mult = 1;
}
while (val < end && ISSPACE (end[-1]))
--end;
if (val == end)
- goto err;
+ return 0;
if (!simple_atof (val, end, &number))
- goto err;
+ return 0;
+
+ *result = number * mult;
+ return 1;
+}
+
+/* Parse VAL as a number and set its value to CLOSURE (which should
+ point to a long int).
+
+ By default, the value is assumed to be in bytes. If "K", "M", or
+ "G" are appended, the value is multiplied with 1<<10, 1<<20, or
+ 1<<30, respectively. Floating point values are allowed and are
+ cast to integer before use. The idea is to be able to use things
+ like 1.5k instead of "1536".
+
+ The string "inf" is returned as 0.
+
+ In case of error, 0 is returned and memory pointed to by CLOSURE
+ remains unmodified. */
+
+static int
+cmd_bytes (const char *com, const char *val, void *closure)
+{
+ double byte_value;
+ if (!parse_bytes_helper (val, &byte_value))
+ {
+ fprintf (stderr, _("%s: %s: Invalid byte value `%s'\n"),
+ exec_name, com, val);
+ return 0;
+ }
+ *(long *)closure = (long)byte_value;
+ return 1;
+}
- *(long *)closure = (long)(number * mult);
+/* Like cmd_bytes, but CLOSURE is interpreted as a pointer to
+ LARGE_INT. It works by converting the string to double, therefore
+ working with values up to 2^53-1 without loss of precision. This
+ value (8192 TB) is large enough to serve for a while. */
+
+static int
+cmd_bytes_large (const char *com, const char *val, void *closure)
+{
+ double byte_value;
+ if (!parse_bytes_helper (val, &byte_value))
+ {
+ fprintf (stderr, _("%s: %s: Invalid byte value `%s'\n"),
+ exec_name, com, val);
+ return 0;
+ }
+ *(LARGE_INT *)closure = (LARGE_INT)byte_value;
return 1;
}