Forward port changelog
[tor.git] / src / or / config.c
bloba7d29a49dc4353db345a0b69f653d46890a0238a
1 /* Copyright 2001 Matej Pfajfar.
2 * Copyright 2001-2004 Roger Dingledine.
3 * Copyright 2004 Roger Dingledine, Nick Mathewson. */
4 /* See LICENSE for licensing information */
5 /* $Id$ */
6 const char config_c_id[] = "$Id$";
8 /**
9 * \file config.c
11 * \brief Code to parse and interpret configuration files.
12 **/
14 #include "or.h"
15 #ifdef MS_WINDOWS
16 #include <shlobj.h>
17 #endif
18 #include "../common/aes.h"
20 /** Enumeration of types which option values can take */
21 typedef enum config_type_t {
22 CONFIG_TYPE_STRING = 0, /**< An arbitrary string. */
23 CONFIG_TYPE_UINT, /**< A non-negative integer less than MAX_INT */
24 CONFIG_TYPE_INTERVAL, /**< A number of seconds, with optional units*/
25 CONFIG_TYPE_MEMUNIT, /**< A number of bytes, with optional units*/
26 CONFIG_TYPE_DOUBLE, /**< A floating-point value */
27 CONFIG_TYPE_BOOL, /**< A boolean value, expressed as 0 or 1. */
28 CONFIG_TYPE_CSV, /**< A list of strings, separated by commas and optional
29 * whitespace. */
30 CONFIG_TYPE_LINELIST, /**< Uninterpreted config lines */
31 CONFIG_TYPE_LINELIST_S, /**< Uninterpreted, context-sensitive config lines,
32 * mixed with other keywords. */
33 CONFIG_TYPE_LINELIST_V, /**< Catch-all "virtual" option to summarize
34 * context-sensitive config lines when fetching.
36 CONFIG_TYPE_OBSOLETE, /**< Obsolete (ignored) option. */
37 } config_type_t;
39 /* An abbreviation for a configuration option allowed on the command line */
40 typedef struct config_abbrev_t {
41 const char *abbreviated;
42 const char *full;
43 int commandline_only;
44 } config_abbrev_t;
46 /* Handy macro for declaring "In the config file or on the command line,
47 * you can abbreviate <b>tok</b>s as <b>tok</b>". */
48 #define PLURAL(tok) { #tok, #tok "s", 0 }
50 /* A list of command-line abbreviations. */
51 static config_abbrev_t config_abbrevs[] = {
52 PLURAL(ExitNode),
53 PLURAL(EntryNode),
54 PLURAL(ExcludeNode),
55 PLURAL(FirewallPort),
56 PLURAL(LongLivedPort),
57 PLURAL(HiddenServiceNode),
58 PLURAL(HiddenServiceExcludeNode),
59 PLURAL(RendNode),
60 PLURAL(RendExcludeNode),
61 PLURAL(StrictEntryNode),
62 PLURAL(StrictExitNode),
63 { "l", "Log", 1},
64 { "BandwidthRateBytes", "BandwidthRate", 0},
65 { "BandwidthBurstBytes", "BandwidthBurst", 0},
66 { "DirFetchPostPeriod", "StatusFetchPeriod", 0},
67 { NULL, NULL , 0},
69 #undef PLURAL
71 /** A variable allowed in the configuration file or on the command line. */
72 typedef struct config_var_t {
73 const char *name; /**< The full keyword (case insensitive). */
74 config_type_t type; /**< How to interpret the type and turn it into a value. */
75 off_t var_offset; /**< Offset of the corresponding member of or_options_t. */
76 const char *initvalue; /**< String (or null) describing initial value. */
77 } config_var_t;
79 /** Return the offset of <b>member</b> within the type <b>tp</b>, in bytes */
80 #define STRUCT_OFFSET(tp, member) ((off_t) (((char*)&((tp*)0)->member)-(char*)0))
81 /** An entry for config_vars: "The option <b>name</b> has type
82 * CONFIG_TYPE_<b>conftype</b>, and corresponds to
83 * or_options_t.<b>member</b>"
85 #define VAR(name,conftype,member,initvalue) \
86 { name, CONFIG_TYPE_ ## conftype, STRUCT_OFFSET(or_options_t, member), initvalue }
87 /** An entry for config_vars: "The option <b>name</b> is obsolete." */
88 #define OBSOLETE(name) { name, CONFIG_TYPE_OBSOLETE, 0, NULL }
90 /** Array of configuration options. Until we disallow nonstandard
91 * abbreviations, order is significant, since the first matching option will
92 * be chosen first.
94 static config_var_t config_vars[] = {
95 VAR("Address", STRING, Address, NULL),
96 VAR("AccountingStart", STRING, AccountingStart, NULL),
97 VAR("AllowUnverifiedNodes",CSV, AllowUnverifiedNodes, "middle,rendezvous"),
98 VAR("AuthoritativeDirectory",BOOL, AuthoritativeDir, "0"),
99 VAR("BandwidthRate", MEMUNIT, BandwidthRate, "1 MB"),
100 VAR("BandwidthBurst", MEMUNIT, BandwidthBurst, "5 MB"),
101 VAR("ClientOnly", BOOL, ClientOnly, "0"),
102 VAR("ContactInfo", STRING, ContactInfo, NULL),
103 VAR("ControlPort", UINT, ControlPort, "0"),
104 VAR("CookieAuthentication",BOOL, CookieAuthentication, "0"),
105 VAR("DebugLogFile", STRING, DebugLogFile, NULL),
106 VAR("DataDirectory", STRING, DataDirectory, NULL),
107 VAR("DirAllowPrivateAddresses",BOOL, DirAllowPrivateAddresses, NULL),
108 VAR("DirPort", UINT, DirPort, "0"),
109 VAR("DirBindAddress", LINELIST, DirBindAddress, NULL),
110 /* XXX we'd like dirfetchperiod to be higher for people with dirport not
111 * set, but low for people with dirport set. how to have two defaults? */
112 VAR("DirFetchPeriod", INTERVAL, DirFetchPeriod, "1 hour"),
113 VAR("DirPostPeriod", INTERVAL, DirPostPeriod, "20 minutes"),
114 VAR("RendPostPeriod", INTERVAL, RendPostPeriod, "20 minutes"),
115 VAR("DirPolicy", LINELIST, DirPolicy, NULL),
116 VAR("DirServer", LINELIST, DirServers, NULL),
117 VAR("ExitNodes", STRING, ExitNodes, NULL),
118 VAR("EntryNodes", STRING, EntryNodes, NULL),
119 VAR("StrictExitNodes", BOOL, StrictExitNodes, "0"),
120 VAR("StrictEntryNodes", BOOL, StrictEntryNodes, "0"),
121 VAR("ExitPolicy", LINELIST, ExitPolicy, NULL),
122 VAR("ExcludeNodes", STRING, ExcludeNodes, NULL),
123 VAR("FascistFirewall", BOOL, FascistFirewall, "0"),
124 VAR("FirewallPorts", CSV, FirewallPorts, "80,443"),
125 VAR("MyFamily", STRING, MyFamily, NULL),
126 VAR("NodeFamily", LINELIST, NodeFamilies, NULL),
127 VAR("Group", STRING, Group, NULL),
128 VAR("HashedControlPassword",STRING, HashedControlPassword, NULL),
129 VAR("HttpProxy", STRING, HttpProxy, NULL),
130 VAR("HiddenServiceOptions",LINELIST_V, RendConfigLines, NULL),
131 VAR("HiddenServiceDir", LINELIST_S, RendConfigLines, NULL),
132 VAR("HiddenServicePort", LINELIST_S, RendConfigLines, NULL),
133 VAR("HiddenServiceNodes", LINELIST_S, RendConfigLines, NULL),
134 VAR("HiddenServiceExcludeNodes", LINELIST_S, RendConfigLines, NULL),
135 VAR("IgnoreVersion", BOOL, IgnoreVersion, "0"),
136 VAR("KeepalivePeriod", INTERVAL, KeepalivePeriod, "5 minutes"),
137 VAR("Log", LINELIST, Logs, NULL),
138 VAR("LogLevel", LINELIST_S, OldLogOptions, NULL),
139 VAR("LogFile", LINELIST_S, OldLogOptions, NULL),
140 OBSOLETE("LinkPadding"),
141 VAR("MaxConn", UINT, MaxConn, "1024"),
142 VAR("MaxOnionsPending", UINT, MaxOnionsPending, "100"),
143 VAR("MonthlyAccountingStart",UINT, _MonthlyAccountingStart,"0"),
144 VAR("AccountingMaxKB", UINT, _AccountingMaxKB, "0"),
145 VAR("AccountingMax", MEMUNIT, AccountingMax, "0 bytes"),
146 VAR("Nickname", STRING, Nickname, NULL),
147 VAR("NewCircuitPeriod", INTERVAL, NewCircuitPeriod, "30 seconds"),
148 VAR("MaxCircuitDirtiness", INTERVAL, MaxCircuitDirtiness, "10 minutes"),
149 VAR("NumCpus", UINT, NumCpus, "1"),
150 VAR("ORPort", UINT, ORPort, "0"),
151 VAR("ORBindAddress", LINELIST, ORBindAddress, NULL),
152 VAR("OutboundBindAddress", STRING, OutboundBindAddress, NULL),
153 VAR("PidFile", STRING, PidFile, NULL),
154 VAR("LongLivedPorts", CSV, LongLivedPorts, "21,22,706,1863,5050,5190,5222,5223,6667,8300,8888"),
155 VAR("PathlenCoinWeight", DOUBLE, PathlenCoinWeight, "0.3"),
156 VAR("RedirectExit", LINELIST, RedirectExit, NULL),
157 OBSOLETE("RouterFile"),
158 VAR("RunAsDaemon", BOOL, RunAsDaemon, "0"),
159 VAR("RunTesting", BOOL, RunTesting, "0"),
160 VAR("RecommendedVersions", LINELIST, RecommendedVersions, NULL),
161 VAR("RendNodes", STRING, RendNodes, NULL),
162 VAR("RendExcludeNodes", STRING, RendExcludeNodes, NULL),
163 VAR("SocksPort", UINT, SocksPort, "9050"),
164 VAR("SocksBindAddress", LINELIST, SocksBindAddress, NULL),
165 VAR("SocksPolicy", LINELIST, SocksPolicy, NULL),
166 /* XXX as with dirfetchperiod, we want this to be 15 minutes for people
167 * with a dirport open, but higher for people without a dirport open. */
168 VAR("StatusFetchPeriod", INTERVAL, StatusFetchPeriod, "15 minutes"),
169 VAR("SysLog", LINELIST_S, OldLogOptions, NULL),
170 OBSOLETE("TrafficShaping"),
171 VAR("User", STRING, User, NULL),
172 { NULL, CONFIG_TYPE_OBSOLETE, 0, NULL }
174 #undef VAR
175 #undef OBSOLETE
177 /** Largest allowed config line */
178 #define CONFIG_LINE_T_MAXLEN 4096
180 static void config_line_append(struct config_line_t **lst,
181 const char *key, const char *val);
182 static void option_reset(or_options_t *options, config_var_t *var);
183 static void options_free(or_options_t *options);
184 static int option_is_same(or_options_t *o1, or_options_t *o2,const char *name);
185 static or_options_t *options_dup(or_options_t *old);
186 static int options_validate(or_options_t *options);
187 static int options_transition_allowed(or_options_t *old, or_options_t *new);
188 static int check_nickname_list(const char *lst, const char *name);
190 static int parse_dir_server_line(const char *line, int validate_only);
191 static int parse_redirect_line(smartlist_t *result,
192 struct config_line_t *line);
193 static int parse_log_severity_range(const char *range, int *min_out,
194 int *max_out);
195 static int convert_log_option(or_options_t *options,
196 struct config_line_t *level_opt,
197 struct config_line_t *file_opt, int isDaemon);
198 static int add_single_log_option(or_options_t *options, int minSeverity,
199 int maxSeverity,
200 const char *type, const char *fname);
201 static int normalize_log_options(or_options_t *options);
202 static int validate_data_directory(or_options_t *options);
203 static int write_configuration_file(const char *fname, or_options_t *options);
205 static uint64_t config_parse_memunit(const char *s, int *ok);
206 static int config_parse_interval(const char *s, int *ok);
207 static void print_cvs_version(void);
210 * Functions to read and write the global options pointer.
213 /** Command-line and config-file options. */
214 static or_options_t *global_options=NULL;
215 /** Name of most recently read torrc file. */
216 static char *config_fname = NULL;
218 /** Return the currently configured options. */
219 or_options_t *
220 get_options(void) {
221 tor_assert(global_options);
222 return global_options;
225 /** Change the current global options to contain <b>new_val</b> instead
226 * of their current value; free the old value as necessary.
228 void
229 set_options(or_options_t *new_val) {
230 if (global_options)
231 options_free(global_options);
232 global_options = new_val;
235 /** Fetch the active option list, and take actions based on it. All
236 * of the things we do should survive being done repeatedly.
237 * Return 0 if all goes well, return -1 if it's time to die.
239 * Note 1: <b>new_val</b> must have previously been validated with
240 * options_validate(), or Tor may freak out and exit.
242 * Note 2: We haven't moved all the "act on new configuration" logic
243 * here yet. Some is still in do_hup() and other places.
246 options_act(void) {
247 struct config_line_t *cl;
248 or_options_t *options = get_options();
249 static int libevent_initialized = 0;
251 /* XXXX009 We once had a reason to separate start_daemon and finish_daemon:
252 * It let us have the parent process stick around until we were sure Tor
253 * was started. Should we make start_daemon get called earlier? -NM */
254 if (options->RunAsDaemon) {
255 start_daemon(options->DataDirectory);
257 if (!libevent_initialized) {
258 event_init();
259 libevent_initialized = 1;
262 clear_trusted_dir_servers();
263 for (cl = options->DirServers; cl; cl = cl->next) {
264 if (parse_dir_server_line(cl->value, 0)<0) {
265 log_fn(LOG_ERR,
266 "Bug: Previously validated DirServer line could not be added!");
267 return -1;
271 if (rend_config_services(options, 0)<0) {
272 log_fn(LOG_ERR,
273 "Bug: Previously validated hidden services line could not be added!");
274 return -1;
277 /* Setuid/setgid as appropriate */
278 if (options->User || options->Group) {
279 if (switch_id(options->User, options->Group) != 0) {
280 return -1;
284 /* Ensure data directory is private; create if possible. */
285 if (check_private_dir(options->DataDirectory, CPD_CREATE) != 0) {
286 log_fn(LOG_ERR, "Couldn't access/create private data directory %s",
287 options->DataDirectory);
288 return -1;
291 /* Bail out at this point if we're not going to be a server: we want
292 * to not fork, and to log stuff to stderr. */
293 if (options->command != CMD_RUN_TOR)
294 return 0;
296 mark_logs_temp(); /* Close current logs once new logs are open. */
297 if (config_init_logs(options, 0)<0) /* Configure the log(s) */
298 return -1;
299 /* Close the temporary log we used while starting up, if it isn't already
300 * gone. */
301 close_temp_logs();
302 add_callback_log(LOG_NOTICE, LOG_ERR, control_event_logmsg);
304 if (set_max_file_descriptors(options->MaxConn) < 0)
305 return -1;
308 smartlist_t *sl = smartlist_create();
309 for (cl = options->RedirectExit; cl; cl = cl->next) {
310 if (parse_redirect_line(sl, cl)<0)
311 return -1;
313 set_exit_redirects(sl);
316 /* Start backgrounding the process, if requested. */
318 /* Finish backgrounding the process */
319 if (options->RunAsDaemon) {
320 /* We may be calling this for the n'th time (on SIGHUP), but it's safe. */
321 finish_daemon();
324 /* Write our pid to the pid file. If we do not have write permissions we
325 * will log a warning */
326 if (options->PidFile)
327 write_pidfile(options->PidFile);
329 /* Update address policies. */
330 parse_socks_policy();
331 parse_dir_policy();
333 init_cookie_authentication(options->CookieAuthentication);
335 /* reload keys as needed for rendezvous services. */
336 if (rend_service_load_keys()<0) {
337 log_fn(LOG_ERR,"Error loading rendezvous service keys");
338 return -1;
341 /* Set up accounting */
342 if (accounting_parse_options(options, 0)<0) {
343 log_fn(LOG_ERR,"Error in accounting options");
344 return -1;
346 if (accounting_is_enabled(options))
347 configure_accounting(time(NULL));
349 if (!we_are_hibernating() && retry_all_listeners(1) < 0) {
350 log_fn(LOG_ERR,"Failed to bind one of the listener ports.");
351 return -1;
354 #if 0
356 char *smin, *smax;
357 smin = config_dump_options(options, 1);
358 smax = config_dump_options(options, 0);
359 log_fn(LOG_DEBUG, "These are our options:\n%s",smax);
360 log_fn(LOG_DEBUG, "We changed these options:\n%s",smin);
361 tor_free(smin);
362 tor_free(smax);
364 #endif
366 /* Since our options changed, we might need to regenerate and upload our
367 * server descriptor. (We could probably be more clever about only calling
368 * this when something significant changed.)
370 mark_my_descriptor_dirty();
372 return 0;
376 * Functions to parse config options
379 /** If <b>option</b> is an official abbreviation for a longer option,
380 * return the longer option. Otherwise return <b>option</b>.
381 * If <b>command_line</b> is set, apply all abbreviations. Otherwise, only
382 * apply abbreviations that work for the config file and the command line. */
383 static const char *
384 expand_abbrev(const char *option, int command_line)
386 int i;
387 for (i=0; config_abbrevs[i].abbreviated; ++i) {
388 /* Abbreviations aren't casei. */
389 if (!strcasecmp(option,config_abbrevs[i].abbreviated) &&
390 (command_line || !config_abbrevs[i].commandline_only)) {
391 return config_abbrevs[i].full;
394 return option;
397 /** Helper: Read a list of configuration options from the command line. */
398 static struct config_line_t *
399 config_get_commandlines(int argc, char **argv)
401 struct config_line_t *new;
402 struct config_line_t *front = NULL;
403 char *s;
404 int i = 1;
406 while (i < argc-1) {
407 if (!strcmp(argv[i],"-f") ||
408 !strcmp(argv[i],"--hash-password")) {
409 i += 2; /* command-line option with argument. ignore them. */
410 continue;
411 } else if (!strcmp(argv[i],"--list-fingerprint")) {
412 i += 1; /* command-line option. ignore it. */
413 continue;
416 new = tor_malloc(sizeof(struct config_line_t));
417 s = argv[i];
419 while (*s == '-')
420 s++;
422 new->key = tor_strdup(expand_abbrev(s, 1));
423 new->value = tor_strdup(argv[i+1]);
425 log(LOG_DEBUG,"Commandline: parsed keyword '%s', value '%s'",
426 new->key, new->value);
427 new->next = front;
428 front = new;
429 i += 2;
431 return front;
434 /** Helper: allocate a new configuration option mapping 'key' to 'val',
435 * append it to *<b>lst</b>. */
436 static void
437 config_line_append(struct config_line_t **lst,
438 const char *key,
439 const char *val)
441 struct config_line_t *newline;
443 newline = tor_malloc(sizeof(struct config_line_t));
444 newline->key = tor_strdup(key);
445 newline->value = tor_strdup(val);
446 newline->next = NULL;
447 while (*lst)
448 lst = &((*lst)->next);
450 (*lst) = newline;
453 /** Helper: parse the config string and strdup into key/value
454 * strings. Set *result to the list, or NULL if parsing the string
455 * failed. Return 0 on success, -1 on failure. Warn and ignore any
456 * misformatted lines. */
458 config_get_lines(char *string, struct config_line_t **result)
460 struct config_line_t *list = NULL, **next;
461 char *k, *v;
463 next = &list;
464 do {
465 string = parse_line_from_str(string, &k, &v);
466 if (!string) {
467 config_free_lines(list);
468 return -1;
470 if (k && v) {
471 /* This list can get long, so we keep a pointer to the end of it
472 * rather than using config_line_append over and over and getting n^2
473 * performance. This is the only really long list. */
474 *next = tor_malloc(sizeof(struct config_line_t));
475 (*next)->key = tor_strdup(k);
476 (*next)->value = tor_strdup(v);
477 (*next)->next = NULL;
478 next = &((*next)->next);
480 } while (*string);
482 *result = list;
483 return 0;
487 * Free all the configuration lines on the linked list <b>front</b>.
489 void
490 config_free_lines(struct config_line_t *front)
492 struct config_line_t *tmp;
494 while (front) {
495 tmp = front;
496 front = tmp->next;
498 tor_free(tmp->key);
499 tor_free(tmp->value);
500 tor_free(tmp);
504 /** If <b>key</b> is a configuration option, return the corresponding
505 * config_var_t. Otherwise, if <b>key</b> is a non-standard abbreviation,
506 * warn, and return the corresponding config_var_t. Otherwise return NULL.
508 static config_var_t *config_find_option(const char *key)
510 int i;
511 size_t keylen = strlen(key);
512 if(!keylen)
513 return NULL; /* if they say "--" on the commandline, it's not an option */
514 /* First, check for an exact (case-insensitive) match */
515 for (i=0; config_vars[i].name; ++i) {
516 if (!strcasecmp(key, config_vars[i].name))
517 return &config_vars[i];
519 /* If none, check for an abbreviated match */
520 for (i=0; config_vars[i].name; ++i) {
521 if (!strncasecmp(key, config_vars[i].name, keylen)) {
522 log_fn(LOG_WARN, "The abbreviation '%s' is deprecated. "
523 "Tell Nick and Roger to make it official, or just use '%s' instead",
524 key, config_vars[i].name);
525 return &config_vars[i];
528 /* Okay, unrecognized options */
529 return NULL;
532 /** If <b>c</b> is a syntactically valid configuration line, update
533 * <b>options</b> with its value and return 0. Otherwise return -1 for bad key,
534 * -2 for bad value.
536 * If 'reset' is set, and we get a line containing no value, restore the
537 * option to its default value.
539 static int
540 config_assign_line(or_options_t *options, struct config_line_t *c, int reset)
542 int i, ok;
543 config_var_t *var;
544 void *lvalue;
546 var = config_find_option(c->key);
547 if (!var) {
548 log_fn(LOG_WARN, "Unknown option '%s'. Failing.", c->key);
549 return -1;
551 /* Put keyword into canonical case. */
552 if (strcmp(var->name, c->key)) {
553 tor_free(c->key);
554 c->key = tor_strdup(var->name);
557 if (reset && !strlen(c->value)) {
558 option_reset(options, var);
559 return 0;
562 lvalue = ((char*)options) + var->var_offset;
563 switch (var->type) {
565 case CONFIG_TYPE_UINT:
566 i = tor_parse_long(c->value, 10, 0, INT_MAX, &ok, NULL);
567 if (!ok) {
568 log(LOG_WARN, "Int keyword '%s %s' is malformed or out of bounds.",
569 c->key,c->value);
570 return -2;
572 *(int *)lvalue = i;
573 break;
575 case CONFIG_TYPE_INTERVAL: {
576 i = config_parse_interval(c->value, &ok);
577 if (!ok) {
578 return -2;
580 *(int *)lvalue = i;
581 break;
584 case CONFIG_TYPE_MEMUNIT: {
585 uint64_t u64 = config_parse_memunit(c->value, &ok);
586 if (!ok) {
587 return -2;
589 *(uint64_t *)lvalue = u64;
590 break;
593 case CONFIG_TYPE_BOOL:
594 i = tor_parse_long(c->value, 10, 0, 1, &ok, NULL);
595 if (!ok) {
596 log(LOG_WARN, "Boolean keyword '%s' expects 0 or 1.", c->key);
597 return -2;
599 *(int *)lvalue = i;
600 break;
602 case CONFIG_TYPE_STRING:
603 tor_free(*(char **)lvalue);
604 *(char **)lvalue = tor_strdup(c->value);
605 break;
607 case CONFIG_TYPE_DOUBLE:
608 *(double *)lvalue = atof(c->value);
609 break;
611 case CONFIG_TYPE_CSV:
612 if (*(smartlist_t**)lvalue) {
613 SMARTLIST_FOREACH(*(smartlist_t**)lvalue, char *, cp, tor_free(cp));
614 smartlist_clear(*(smartlist_t**)lvalue);
615 } else {
616 *(smartlist_t**)lvalue = smartlist_create();
619 smartlist_split_string(*(smartlist_t**)lvalue, c->value, ",",
620 SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
621 break;
623 case CONFIG_TYPE_LINELIST:
624 case CONFIG_TYPE_LINELIST_S:
625 config_line_append((struct config_line_t**)lvalue, c->key, c->value);
626 break;
628 case CONFIG_TYPE_OBSOLETE:
629 log_fn(LOG_WARN, "Skipping obsolete configuration option '%s'", c->key);
630 break;
631 case CONFIG_TYPE_LINELIST_V:
632 log_fn(LOG_WARN, "Can't provide value for virtual option '%s'", c->key);
633 return -2;
634 default:
635 tor_assert(0);
636 break;
638 return 0;
641 /** restore the option named <b>key</b> in options to its default value. */
642 static void
643 config_reset_line(or_options_t *options, const char *key)
645 config_var_t *var;
647 var = config_find_option(key);
648 if (!var)
649 return; /* give error on next pass. */
651 option_reset(options, var);
654 /** Return true iff key is a valid configuration option. */
656 config_option_is_recognized(const char *key)
658 config_var_t *var = config_find_option(key);
659 return (var != NULL);
662 /** Return a canonicalized list of the options assigned for key.
664 struct config_line_t *
665 config_get_assigned_option(or_options_t *options, const char *key)
667 config_var_t *var;
668 const void *value;
669 char buf[32];
670 struct config_line_t *result;
671 tor_assert(options && key);
673 var = config_find_option(key);
674 if (!var) {
675 log_fn(LOG_WARN, "Unknown option '%s'. Failing.", key);
676 return NULL;
677 } else if (var->type == CONFIG_TYPE_LINELIST_S) {
678 log_fn(LOG_WARN, "Can't return context-sensitive '%s' on its own", key);
679 return NULL;
681 value = ((char*)options) + var->var_offset;
683 if (var->type == CONFIG_TYPE_LINELIST ||
684 var->type == CONFIG_TYPE_LINELIST_V) {
685 /* Linelist requires special handling: we just copy and return it. */
686 const struct config_line_t *next_in = *(const struct config_line_t**)value;
687 struct config_line_t **next_out = &result;
688 while (next_in) {
689 *next_out = tor_malloc(sizeof(struct config_line_t));
690 (*next_out)->key = tor_strdup(next_in->key);
691 (*next_out)->value = tor_strdup(next_in->value);
692 next_in = next_in->next;
693 next_out = &((*next_out)->next);
695 (*next_out) = NULL;
696 return result;
699 result = tor_malloc_zero(sizeof(struct config_line_t));
700 result->key = tor_strdup(var->name);
701 switch (var->type)
703 case CONFIG_TYPE_STRING:
704 if (*(char**)value) {
705 result->value = tor_strdup(*(char**)value);
706 } else {
707 tor_free(result->key);
708 tor_free(result);
709 return NULL;
711 break;
712 case CONFIG_TYPE_INTERVAL:
713 case CONFIG_TYPE_UINT:
714 /* This means every or_options_t uint or bool element
715 * needs to be an int. Not, say, a uint16_t or char. */
716 tor_snprintf(buf, sizeof(buf), "%d", *(int*)value);
717 result->value = tor_strdup(buf);
718 break;
719 case CONFIG_TYPE_MEMUNIT:
720 tor_snprintf(buf, sizeof(buf), U64_FORMAT,
721 U64_PRINTF_ARG(*(uint64_t*)value));
722 result->value = tor_strdup(buf);
723 break;
724 case CONFIG_TYPE_DOUBLE:
725 tor_snprintf(buf, sizeof(buf), "%f", *(double*)value);
726 result->value = tor_strdup(buf);
727 break;
728 case CONFIG_TYPE_BOOL:
729 result->value = tor_strdup(*(int*)value ? "1" : "0");
730 break;
731 case CONFIG_TYPE_CSV:
732 if (*(smartlist_t**)value)
733 result->value = smartlist_join_strings(*(smartlist_t**)value,",",0,NULL);
734 else
735 result->value = tor_strdup("");
736 break;
737 case CONFIG_TYPE_OBSOLETE:
738 log_fn(LOG_WARN,"You asked me for the value of an obsolete config option %s.", key);
739 tor_free(result->key);
740 tor_free(result);
741 return NULL;
742 default:
743 tor_free(result->key);
744 tor_free(result);
745 log_fn(LOG_WARN,"Bug: unknown type %d for known key %s", var->type, key);
746 return NULL;
749 return result;
752 /** Iterate through the linked list of requested options <b>list</b>.
753 * For each item, convert as appropriate and assign to <b>options</b>.
754 * If an item is unrecognized, return -1 immediately,
755 * else return 0 for success.
757 * If <b>reset</b>, then interpret empty lines as meaning "restore to
758 * default value", and interpret LINELIST* options as replacing (not
759 * extending) their previous values. Return 0 on success, -1 on bad key,
760 * -2 on bad value.
762 static int
763 config_assign(or_options_t *options, struct config_line_t *list, int reset)
765 struct config_line_t *p;
766 tor_assert(options);
768 /* pass 1: normalize keys */
769 for (p = list; p; p = p->next) {
770 const char *full = expand_abbrev(p->key, 0);
771 if (strcmp(full,p->key)) {
772 tor_free(p->key);
773 p->key = tor_strdup(full);
777 /* pass 2: if we're reading from a resetting source, clear all mentioned
778 * linelists. */
779 if (reset) {
780 for (p = list; p; p = p->next)
781 config_reset_line(options, p->key);
784 /* pass 3: assign. */
785 while (list) {
786 int r;
787 if ((r=config_assign_line(options, list, reset)))
788 return r;
789 list = list->next;
791 return 0;
794 /** Try assigning <b>list</b> to the global options. You do this by duping
795 * options, assigning list to the new one, then validating it. If it's
796 * ok, then throw out the old one and stick with the new one. Else,
797 * revert to old and return failure. Return 0 on success, -1 on bad
798 * keys, -2 on bad values, -3 on bad transition.
801 config_trial_assign(struct config_line_t *list, int reset)
803 int r;
804 or_options_t *trial_options = options_dup(get_options());
806 if ((r=config_assign(trial_options, list, reset)) < 0) {
807 options_free(trial_options);
808 return r;
811 if (options_validate(trial_options) < 0) {
812 options_free(trial_options);
813 return -2;
816 if (options_transition_allowed(get_options(), trial_options) < 0) {
817 options_free(trial_options);
818 return -3;
821 set_options(trial_options); /* we liked it. put it in place. */
822 return 0;
825 /** Replace the option indexed by <b>var</b> in <b>options</b> with its
826 * default value. */
827 static void
828 option_reset(or_options_t *options, config_var_t *var)
830 struct config_line_t *c;
831 void *lvalue;
833 lvalue = ((char*)options) + var->var_offset;
834 switch (var->type) {
835 case CONFIG_TYPE_STRING:
836 tor_free(*(char**)lvalue);
837 break;
838 case CONFIG_TYPE_DOUBLE:
839 *(double*)lvalue = 0.0;
840 break;
841 case CONFIG_TYPE_INTERVAL:
842 case CONFIG_TYPE_UINT:
843 case CONFIG_TYPE_BOOL:
844 *(int*)lvalue = 0;
845 break;
846 case CONFIG_TYPE_MEMUNIT:
847 *(uint64_t*)lvalue = 0;
848 break;
849 case CONFIG_TYPE_CSV:
850 if (*(smartlist_t**)lvalue) {
851 SMARTLIST_FOREACH(*(smartlist_t **)lvalue, char *, cp, tor_free(cp));
852 smartlist_free(*(smartlist_t **)lvalue);
853 *(smartlist_t **)lvalue = NULL;
855 break;
856 case CONFIG_TYPE_LINELIST:
857 case CONFIG_TYPE_LINELIST_S:
858 config_free_lines(*(struct config_line_t **)lvalue);
859 *(struct config_line_t **)lvalue = NULL;
860 break;
861 case CONFIG_TYPE_LINELIST_V:
862 /* handled by linelist_s. */
863 break;
864 case CONFIG_TYPE_OBSOLETE:
865 break;
867 if (var->initvalue) {
868 c = tor_malloc_zero(sizeof(struct config_line_t));
869 c->key = tor_strdup(var->name);
870 c->value = tor_strdup(var->initvalue);
871 config_assign_line(options,c,0);
872 config_free_lines(c);
876 /** Set <b>options</b>-&gt;DirServers to contain the default directory
877 * servers. */
878 static void
879 add_default_trusted_dirservers(or_options_t *options)
881 /* moria1 */
882 config_line_append(&options->DirServers, "DirServer",
883 "18.244.0.188:9031 FFCB 46DB 1339 DA84 674C 70D7 CB58 6434 C437 0441");
884 /* moria2 */
885 config_line_append(&options->DirServers, "DirServer",
886 "18.244.0.114:80 719B E45D E224 B607 C537 07D0 E214 3E2D 423E 74CF");
887 /* tor26 */
888 config_line_append(&options->DirServers, "DirServer",
889 "62.116.124.106:9030 847B 1F85 0344 D787 6491 A548 92F9 0493 4E4E B85D");
890 // "tor.noreply.org:9030 847B 1F85 0344 D787 6491 A548 92F9 0493 4E4E B85D");
893 /** Print a usage message for tor. */
894 static void
895 print_usage(void)
897 printf(
898 "Copyright 2001-2004 Roger Dingledine, Nick Mathewson, Matej Pfajfar.\n\n"
899 "tor -f <torrc> [args]\n"
900 "See man page for options, or http://tor.eff.org/ for documentation.\n");
904 * Based on <b>address</b>, guess our public IP address and put it
905 * in <b>addr</b>.
908 resolve_my_address(const char *address, uint32_t *addr)
910 struct in_addr in;
911 struct hostent *rent;
912 char hostname[256];
913 int explicit_ip=1;
915 tor_assert(addr);
917 if (address) {
918 strlcpy(hostname, address, sizeof(hostname));
919 } else { /* then we need to guess our address */
920 explicit_ip = 0; /* it's implicit */
922 if (gethostname(hostname, sizeof(hostname)) < 0) {
923 log_fn(LOG_WARN,"Error obtaining local hostname");
924 return -1;
926 log_fn(LOG_DEBUG,"Guessed local host name as '%s'",hostname);
929 /* now we know hostname. resolve it and keep only the IP */
931 if (tor_inet_aton(hostname, &in) == 0) {
932 /* then we have to resolve it */
933 explicit_ip = 0;
934 rent = (struct hostent *)gethostbyname(hostname);
935 if (!rent) {
936 log_fn(LOG_WARN,"Could not resolve local Address %s. Failing.", hostname);
937 return -1;
939 tor_assert(rent->h_length == 4);
940 memcpy(&in.s_addr, rent->h_addr, rent->h_length);
943 if (!explicit_ip && is_internal_IP(htonl(in.s_addr))) {
944 log_fn(LOG_WARN,"Address '%s' resolves to private IP '%s'. "
945 "Please set the Address config option to be the IP you want to use.",
946 hostname, inet_ntoa(in));
947 return -1;
950 log_fn(LOG_DEBUG, "Resolved Address to %s.", inet_ntoa(in));
951 *addr = ntohl(in.s_addr);
952 return 0;
955 /** Called when we don't have a nickname set. Try to guess a good
956 * nickname based on the hostname, and return it in a newly allocated string. */
957 static char *
958 get_default_nickname(void)
960 char localhostname[256];
961 char *cp, *out, *outp;
963 if (gethostname(localhostname, sizeof(localhostname)) < 0) {
964 log_fn(LOG_WARN,"Error obtaining local hostname");
965 return NULL;
968 /* Put it in lowercase; stop at the first dot. */
969 for (cp = localhostname; *cp; ++cp) {
970 if (*cp == '.') {
971 *cp = '\0';
972 break;
974 *cp = tolower(*cp);
977 /* Strip invalid characters. */
978 cp = localhostname;
979 out = outp = tor_malloc(strlen(localhostname) + 1);
980 while (*cp) {
981 if (strchr(LEGAL_NICKNAME_CHARACTERS, *cp))
982 *outp++ = *cp++;
983 else
984 cp++;
986 *outp = '\0';
988 /* Enforce length. */
989 if (strlen(out) > MAX_NICKNAME_LEN)
990 out[MAX_NICKNAME_LEN]='\0';
992 return out;
995 /** Release storage held by <b>options</b> */
996 static void
997 options_free(or_options_t *options)
999 int i;
1000 void *lvalue;
1002 tor_assert(options);
1004 for (i=0; config_vars[i].name; ++i) {
1005 lvalue = ((char*)options) + config_vars[i].var_offset;
1006 switch (config_vars[i].type) {
1007 case CONFIG_TYPE_MEMUNIT:
1008 case CONFIG_TYPE_INTERVAL:
1009 case CONFIG_TYPE_UINT:
1010 case CONFIG_TYPE_BOOL:
1011 case CONFIG_TYPE_DOUBLE:
1012 case CONFIG_TYPE_OBSOLETE:
1013 break; /* nothing to free for these config types */
1014 case CONFIG_TYPE_STRING:
1015 tor_free(*(char **)lvalue);
1016 break;
1017 case CONFIG_TYPE_LINELIST:
1018 case CONFIG_TYPE_LINELIST_V:
1019 config_free_lines(*(struct config_line_t**)lvalue);
1020 *(struct config_line_t**)lvalue = NULL;
1021 break;
1022 case CONFIG_TYPE_CSV:
1023 if (*(smartlist_t**)lvalue) {
1024 SMARTLIST_FOREACH(*(smartlist_t**)lvalue, char *, cp, tor_free(cp));
1025 smartlist_free(*(smartlist_t**)lvalue);
1026 *(smartlist_t**)lvalue = NULL;
1028 break;
1029 case CONFIG_TYPE_LINELIST_S:
1030 /* will be freed by corresponding LINELIST_V. */
1031 break;
1034 tor_free(options);
1037 /** Return true iff the option <b>var</b> has the same value in <b>o1</b>
1038 * and <b>o2</b>. Must not be called for LINELIST_S or OBSOLETE options.
1040 static int
1041 option_is_same(or_options_t *o1, or_options_t *o2, const char *name)
1043 struct config_line_t *c1, *c2;
1044 int r = 1;
1045 c1 = config_get_assigned_option(o1, name);
1046 c2 = config_get_assigned_option(o2, name);
1047 while (c1 && c2) {
1048 if (strcasecmp(c1->key, c2->key) ||
1049 strcmp(c1->value, c2->value)) {
1050 r = 0;
1051 break;
1053 c1 = c1->next;
1054 c2 = c2->next;
1056 if (r && (c1 || c2)) {
1057 r = 0;
1059 config_free_lines(c1);
1060 config_free_lines(c2);
1061 return r;
1064 /** Copy storage held by <b>old</b> into a new or_options_t and return it. */
1065 static or_options_t *
1066 options_dup(or_options_t *old)
1068 or_options_t *newopts;
1069 int i;
1070 struct config_line_t *line;
1072 newopts = tor_malloc_zero(sizeof(or_options_t));
1073 for (i=0; config_vars[i].name; ++i) {
1074 if (config_vars[i].type == CONFIG_TYPE_LINELIST_S)
1075 continue;
1076 if (config_vars[i].type == CONFIG_TYPE_OBSOLETE)
1077 continue;
1078 line = config_get_assigned_option(old, config_vars[i].name);
1079 if (line) {
1080 if (config_assign(newopts, line, 0) < 0) {
1081 log_fn(LOG_WARN,"Bug: config_get_assigned_option() generated "
1082 "something we couldn't config_assign().");
1083 tor_assert(0);
1086 config_free_lines(line);
1088 return newopts;
1091 /** Set <b>options</b> to hold reasonable defaults for most options.
1092 * Each option defaults to zero. */
1093 void
1094 options_init(or_options_t *options)
1096 int i;
1097 config_var_t *var;
1099 for (i=0; config_vars[i].name; ++i) {
1100 var = &config_vars[i];
1101 if (!var->initvalue)
1102 continue; /* defaults to NULL or 0 */
1103 option_reset(options, var);
1107 /** Return a string containing a possible configuration file that would give
1108 * the configuration in <b>options</b>. If <b>minimal</b> is true, do not
1109 * include options that are the same as Tor's defaults.
1111 char *
1112 config_dump_options(or_options_t *options, int minimal)
1114 smartlist_t *elements;
1115 or_options_t *defaults;
1116 struct config_line_t *line;
1117 char *result;
1118 int i;
1120 defaults = tor_malloc_zero(sizeof(or_options_t));
1121 options_init(defaults);
1122 options_validate(defaults); /* ??? will this work? */
1124 elements = smartlist_create();
1125 for (i=0; config_vars[i].name; ++i) {
1126 if (config_vars[i].type == CONFIG_TYPE_OBSOLETE ||
1127 config_vars[i].type == CONFIG_TYPE_LINELIST_S)
1128 continue;
1129 if (minimal && option_is_same(options, defaults, config_vars[i].name))
1130 continue;
1131 line = config_get_assigned_option(options, config_vars[i].name);
1132 for (; line; line = line->next) {
1133 size_t len = strlen(line->key) + strlen(line->value) + 3;
1134 char *tmp;
1135 tmp = tor_malloc(len);
1136 if (tor_snprintf(tmp, len, "%s %s\n", line->key, line->value)<0) {
1137 log_fn(LOG_ERR, "Internal error writing log option");
1138 tor_assert(0);
1140 smartlist_add(elements, tmp);
1142 config_free_lines(line);
1145 result = smartlist_join_strings(elements, "", 0, NULL);
1146 SMARTLIST_FOREACH(elements, char *, cp, tor_free(cp));
1147 smartlist_free(elements);
1148 return result;
1151 static int
1152 validate_ports_csv(smartlist_t *sl, char *name) {
1153 int i;
1154 int result = 0;
1155 tor_assert(name);
1157 if(!sl)
1158 return 0;
1160 SMARTLIST_FOREACH(sl, const char *, cp,
1162 i = atoi(cp);
1163 if (i < 1 || i > 65535) {
1164 log(LOG_WARN, "Port '%s' out of range in %s", cp, name);
1165 result=-1;
1168 return result;
1171 /** Return 0 if every setting in <b>options</b> is reasonable. Else
1172 * warn and return -1. Should have no side effects, except for
1173 * normalizing the contents of <b>options</b>. */
1174 static int
1175 options_validate(or_options_t *options)
1177 int result = 0;
1178 struct config_line_t *cl;
1179 addr_policy_t *addr_policy=NULL;
1181 if (options->ORPort < 0 || options->ORPort > 65535) {
1182 log(LOG_WARN, "ORPort option out of bounds.");
1183 result = -1;
1186 /* XXX might similarly want to check the other *BindAddress options */
1187 if (options->ORPort == 0 && options->ORBindAddress != NULL) {
1188 log(LOG_WARN, "ORPort must be defined if ORBindAddress is defined.");
1189 result = -1;
1192 if (validate_data_directory(options)<0) {
1193 log(LOG_WARN, "Invalid DataDirectory");
1194 result = -1;
1197 if (options->Nickname == NULL) {
1198 if (server_mode(options)) {
1199 if (!(options->Nickname = get_default_nickname()))
1200 return -1;
1201 log_fn(LOG_NOTICE, "Choosing default nickname %s", options->Nickname);
1203 } else {
1204 if (strspn(options->Nickname, LEGAL_NICKNAME_CHARACTERS) !=
1205 strlen(options->Nickname)) {
1206 log_fn(LOG_WARN, "Nickname '%s' contains illegal characters.", options->Nickname);
1207 result = -1;
1209 if (strlen(options->Nickname) == 0) {
1210 log_fn(LOG_WARN, "Nickname must have at least one character");
1211 result = -1;
1213 if (strlen(options->Nickname) > MAX_NICKNAME_LEN) {
1214 log_fn(LOG_WARN, "Nickname '%s' has more than %d characters.",
1215 options->Nickname, MAX_NICKNAME_LEN);
1216 result = -1;
1220 if (normalize_log_options(options))
1221 return -1;
1223 /* Special case if no options are given. */
1224 if (!options->Logs) {
1225 config_line_append(&options->Logs, "Log", "notice stdout");
1228 if (config_init_logs(options, 1)<0) /* Validate the log(s) */
1229 return -1;
1231 if (server_mode(options)) {
1232 /* confirm that our address isn't broken, so we can complain now */
1233 uint32_t tmp;
1234 if (resolve_my_address(options->Address, &tmp) < 0)
1235 result = -1;
1238 if (options->SocksPort < 0 || options->SocksPort > 65535) {
1239 log(LOG_WARN, "SocksPort option out of bounds.");
1240 result = -1;
1243 if (options->SocksPort == 0 && options->ORPort == 0) {
1244 log(LOG_WARN, "SocksPort and ORPort are both undefined? Quitting.");
1245 result = -1;
1248 if (options->ControlPort < 0 || options->ControlPort > 65535) {
1249 log(LOG_WARN, "ControlPort option out of bounds.");
1250 result = -1;
1253 if (options->DirPort < 0 || options->DirPort > 65535) {
1254 log(LOG_WARN, "DirPort option out of bounds.");
1255 result = -1;
1258 if (options->StrictExitNodes &&
1259 (!options->ExitNodes || !strlen(options->ExitNodes))) {
1260 log(LOG_WARN, "StrictExitNodes set, but no ExitNodes listed.");
1263 if (options->StrictEntryNodes &&
1264 (!options->EntryNodes || !strlen(options->EntryNodes))) {
1265 log(LOG_WARN, "StrictEntryNodes set, but no EntryNodes listed.");
1268 if (options->AuthoritativeDir && options->RecommendedVersions == NULL) {
1269 log(LOG_WARN, "Directory servers must configure RecommendedVersions.");
1270 result = -1;
1273 if (options->AuthoritativeDir && !options->DirPort) {
1274 log(LOG_WARN, "Running as authoritative directory, but no DirPort set.");
1275 result = -1;
1278 if (options->AuthoritativeDir && !options->ORPort) {
1279 log(LOG_WARN, "Running as authoritative directory, but no ORPort set.");
1280 result = -1;
1283 if (options->AuthoritativeDir && options->ClientOnly) {
1284 log(LOG_WARN, "Running as authoritative directory, but ClientOnly also set.");
1285 result = -1;
1288 if (options->_AccountingMaxKB) {
1289 log(LOG_WARN, "AccountingMaxKB is deprecated. Say 'AccountingMax %d KB' instead.", options->_AccountingMaxKB);
1290 options->AccountingMax = U64_LITERAL(1024)*options->_AccountingMaxKB;
1291 options->_AccountingMaxKB = 0;
1294 if (validate_ports_csv(options->FirewallPorts,
1295 "FirewallPorts") < 0)
1296 result = -1;
1298 if (validate_ports_csv(options->LongLivedPorts,
1299 "LongLivedPorts") < 0)
1300 result = -1;
1302 options->_AllowUnverified = 0;
1303 if (options->AllowUnverifiedNodes) {
1304 SMARTLIST_FOREACH(options->AllowUnverifiedNodes, const char *, cp, {
1305 if (!strcasecmp(cp, "entry"))
1306 options->_AllowUnverified |= ALLOW_UNVERIFIED_ENTRY;
1307 else if (!strcasecmp(cp, "exit"))
1308 options->_AllowUnverified |= ALLOW_UNVERIFIED_EXIT;
1309 else if (!strcasecmp(cp, "middle"))
1310 options->_AllowUnverified |= ALLOW_UNVERIFIED_MIDDLE;
1311 else if (!strcasecmp(cp, "introduction"))
1312 options->_AllowUnverified |= ALLOW_UNVERIFIED_INTRODUCTION;
1313 else if (!strcasecmp(cp, "rendezvous"))
1314 options->_AllowUnverified |= ALLOW_UNVERIFIED_RENDEZVOUS;
1315 else {
1316 log(LOG_WARN, "Unrecognized value '%s' in AllowUnverifiedNodes",
1317 cp);
1318 result = -1;
1323 if (options->SocksPort >= 1 &&
1324 (options->PathlenCoinWeight < 0.0 || options->PathlenCoinWeight >= 1.0)) {
1325 log(LOG_WARN, "PathlenCoinWeight option must be >=0.0 and <1.0.");
1326 result = -1;
1329 if (options->MaxConn < 1) {
1330 log(LOG_WARN, "MaxConn option must be a non-zero positive integer.");
1331 result = -1;
1334 if (options->MaxConn > MAXCONNECTIONS) {
1335 log(LOG_WARN, "MaxConn option must be at most %d.", MAXCONNECTIONS);
1336 result = -1;
1339 #define MIN_DIR_FETCH_PERIOD 600
1340 #define MIN_DIR_POST_PERIOD 300
1341 #define MIN_REND_POST_PERIOD 300
1342 #define MIN_STATUS_FETCH_PERIOD 60
1344 #define MAX_DIR_PERIOD (MIN_ONION_KEY_LIFETIME/2)
1345 #define MAX_CACHE_DIR_FETCH_PERIOD 3600
1346 #define MAX_CACHE_STATUS_FETCH_PERIOD 900
1348 if (options->DirFetchPeriod < MIN_DIR_FETCH_PERIOD) {
1349 log(LOG_WARN, "DirFetchPeriod option must be at least %d seconds. Clipping.", MIN_DIR_FETCH_PERIOD);
1350 options->DirFetchPeriod = MIN_DIR_FETCH_PERIOD;
1352 if (options->StatusFetchPeriod < MIN_STATUS_FETCH_PERIOD) {
1353 log(LOG_WARN, "StatusFetchPeriod option must be at least %d seconds. Clipping.", MIN_STATUS_FETCH_PERIOD);
1354 options->StatusFetchPeriod = MIN_STATUS_FETCH_PERIOD;
1356 if (options->DirPostPeriod < MIN_DIR_POST_PERIOD) {
1357 log(LOG_WARN, "DirPostPeriod option must be at least %d seconds. Clipping.",
1358 MIN_DIR_POST_PERIOD);
1359 options->DirPostPeriod = MIN_DIR_POST_PERIOD;
1361 if (options->RendPostPeriod < MIN_REND_POST_PERIOD) {
1362 log(LOG_WARN,"RendPostPeriod option must be at least %d seconds. Clipping.",
1363 MIN_REND_POST_PERIOD);
1364 options->RendPostPeriod = MIN_REND_POST_PERIOD;
1367 if (options->DirPort && ! options->AuthoritativeDir) {
1368 if (options->DirFetchPeriod > MAX_CACHE_DIR_FETCH_PERIOD) {
1369 log(LOG_WARN, "Caching directory servers must have DirFetchPeriod less than %d seconds. Clipping.", MAX_CACHE_DIR_FETCH_PERIOD);
1370 options->DirFetchPeriod = MAX_CACHE_DIR_FETCH_PERIOD;
1372 if (options->StatusFetchPeriod > MAX_CACHE_STATUS_FETCH_PERIOD) {
1373 log(LOG_WARN, "Caching directory servers must have StatusFetchPeriod less than %d seconds. Clipping.", MAX_CACHE_STATUS_FETCH_PERIOD);
1374 options->StatusFetchPeriod = MAX_CACHE_STATUS_FETCH_PERIOD;
1378 if (options->DirFetchPeriod > MAX_DIR_PERIOD) {
1379 log(LOG_WARN, "DirFetchPeriod is too large; clipping.");
1380 options->DirFetchPeriod = MAX_DIR_PERIOD;
1382 if (options->DirPostPeriod > MAX_DIR_PERIOD) {
1383 log(LOG_WARN, "DirPostPeriod is too large; clipping.");
1384 options->DirPostPeriod = MAX_DIR_PERIOD;
1386 if (options->StatusFetchPeriod > MAX_DIR_PERIOD) {
1387 log(LOG_WARN, "StatusFetchPeriod is too large; clipping.");
1388 options->StatusFetchPeriod = MAX_DIR_PERIOD;
1390 if (options->RendPostPeriod > MAX_DIR_PERIOD) {
1391 log(LOG_WARN, "RendPostPeriod is too large; clipping.");
1392 options->RendPostPeriod = MAX_DIR_PERIOD;
1395 if (options->KeepalivePeriod < 1) {
1396 log(LOG_WARN,"KeepalivePeriod option must be positive.");
1397 result = -1;
1400 if (options->BandwidthRate > INT_MAX) {
1401 log(LOG_WARN,"BandwidthRate must be less than %d",INT_MAX);
1402 result = -1;
1404 if (options->BandwidthBurst > INT_MAX) {
1405 log(LOG_WARN,"BandwidthBurst must be less than %d",INT_MAX);
1406 result = -1;
1408 if (server_mode(options) &&
1409 options->BandwidthRate < ROUTER_REQUIRED_MIN_BANDWIDTH*2) {
1410 log(LOG_WARN,"BandwidthRate is set to %d bytes/second. For servers, it must be at least %d.", (int)options->BandwidthRate, ROUTER_REQUIRED_MIN_BANDWIDTH*2);
1411 result = -1;
1413 if (options->BandwidthRate > options->BandwidthBurst) {
1414 log(LOG_WARN,"BandwidthBurst must be at least equal to BandwidthRate.");
1415 result = -1;
1417 #if 0
1418 if (2*options->BandwidthRate > options->BandwidthBurst) {
1419 log(LOG_NOTICE,"You have chosen a BandwidthBurst less than twice BandwidthRate. Please consider setting your BandwidthBurst higher (at least %d), to provide better service to the Tor network.", (int)(2*options->BandwidthRate));
1421 #endif
1423 if (options->_MonthlyAccountingStart) {
1424 if (options->AccountingStart) {
1425 log(LOG_WARN,"Can't specify AccountingStart and MonthlyAccountingStart");
1426 result = -1;
1427 } else {
1428 options->AccountingStart = tor_malloc(32);
1429 if (tor_snprintf(options->AccountingStart, 32, "month %d 0:00",
1430 options->_MonthlyAccountingStart)<0) {
1431 log_fn(LOG_WARN,"Error translating MonthlyAccountingStart");
1432 result = -1;
1433 } else {
1434 log_fn(LOG_WARN,"MonthlyAccountingStart is deprecated. Use 'AccountingStart %s' instead.", options->AccountingStart);
1439 if (accounting_parse_options(options, 1)<0) {
1440 result = -1;
1443 if (options->HttpProxy) { /* parse it now */
1444 if (parse_addr_port(options->HttpProxy, NULL,
1445 &options->HttpProxyAddr, &options->HttpProxyPort) < 0) {
1446 log(LOG_WARN,"HttpProxy failed to parse or resolve. Please fix.");
1447 result = -1;
1449 if (options->HttpProxyPort == 0) { /* give it a default */
1450 options->HttpProxyPort = 80;
1454 if (options->HashedControlPassword) {
1455 if (decode_hashed_password(NULL, options->HashedControlPassword)<0) {
1456 log_fn(LOG_WARN,"Bad HashedControlPassword: wrong length or bad base64");
1457 result = -1;
1460 if (options->HashedControlPassword && options->CookieAuthentication) {
1461 log_fn(LOG_WARN,"Cannot enable both HashedControlPassword and CookieAuthentication");
1462 result = -1;
1465 if (check_nickname_list(options->ExitNodes, "ExitNodes"))
1466 result = -1;
1467 if (check_nickname_list(options->EntryNodes, "EntryNodes"))
1468 result = -1;
1469 if (check_nickname_list(options->ExcludeNodes, "ExcludeNodes"))
1470 result = -1;
1471 if (check_nickname_list(options->RendNodes, "RendNodes"))
1472 result = -1;
1473 if (check_nickname_list(options->RendNodes, "RendExcludeNodes"))
1474 result = -1;
1475 if (check_nickname_list(options->MyFamily, "MyFamily"))
1476 result = -1;
1477 for (cl = options->NodeFamilies; cl; cl = cl->next) {
1478 if (check_nickname_list(cl->value, "NodeFamily"))
1479 result = -1;
1482 if (config_parse_addr_policy(options->ExitPolicy, &addr_policy)) {
1483 log_fn(LOG_WARN, "Error in Exit Policy entry.");
1484 result = -1;
1486 if (server_mode(options)) {
1487 exit_policy_implicitly_allows_local_networks(addr_policy, 1);
1489 /* The rest of these calls *append* to addr_policy. So don't actually
1490 * use the results for anything other than checking if they parse! */
1491 if (config_parse_addr_policy(options->DirPolicy, &addr_policy)) {
1492 log_fn(LOG_WARN, "Error in DirPolicy entry.");
1493 result = -1;
1495 if (config_parse_addr_policy(options->SocksPolicy, &addr_policy)) {
1496 log_fn(LOG_WARN, "Error in SocksPolicy entry.");
1497 result = -1;
1499 addr_policy_free(addr_policy);
1501 for (cl = options->RedirectExit; cl; cl = cl->next) {
1502 if (parse_redirect_line(NULL, cl)<0)
1503 result = -1;
1506 if (!options->DirServers) {
1507 add_default_trusted_dirservers(options);
1508 } else {
1509 for (cl = options->DirServers; cl; cl = cl->next) {
1510 if (parse_dir_server_line(cl->value, 1)<0)
1511 result = -1;
1515 if (rend_config_services(options, 1) < 0)
1516 result = -1;
1518 return result;
1521 /** Helper: return true iff s1 and s2 are both NULL, or both non-NULL
1522 * equal strings. */
1523 static int
1524 opt_streq(const char *s1, const char *s2)
1526 if (!s1 && !s2)
1527 return 1;
1528 else if (s1 && s2 && !strcmp(s1,s2))
1529 return 1;
1530 else
1531 return 0;
1534 /** Check if any of the previous options have changed but aren't allowed to. */
1535 static int
1536 options_transition_allowed(or_options_t *old, or_options_t *new_val) {
1538 if (!old)
1539 return 0;
1541 if (!opt_streq(old->PidFile, new_val->PidFile)) {
1542 log_fn(LOG_WARN,"PidFile is not allowed to change. Failing.");
1543 return -1;
1546 if (old->RunAsDaemon && !new_val->RunAsDaemon) {
1547 log_fn(LOG_WARN,"During reload, change from RunAsDaemon=1 to =0 not allowed. Failing.");
1548 return -1;
1551 if (old->ORPort != new_val->ORPort) {
1552 log_fn(LOG_WARN,"During reload, changing ORPort is not allowed. Failing.");
1553 return -1;
1556 if (strcmp(old->DataDirectory,new_val->DataDirectory)!=0) {
1557 log_fn(LOG_WARN,"During reload, changing DataDirectory (%s->%s) is not allowed. Failing.", old->DataDirectory, new_val->DataDirectory);
1558 return -1;
1561 if (!opt_streq(old->User, new_val->User)) {
1562 log_fn(LOG_WARN,"During reload, changing User is not allowed. Failing.");
1563 return -1;
1566 if (!opt_streq(old->Group, new_val->Group)) {
1567 log_fn(LOG_WARN,"During reload, changing User is not allowed. Failing.");
1568 return -1;
1571 return 0;
1574 #ifdef MS_WINDOWS
1575 /** Return the directory on windows where we expect to find our application
1576 * data. */
1577 static char *get_windows_conf_root(void)
1579 static int is_set = 0;
1580 static char path[MAX_PATH+1];
1582 LPITEMIDLIST idl;
1583 IMalloc *m;
1584 HRESULT result;
1586 if (is_set)
1587 return path;
1589 /* Find X:\documents and settings\username\application data\ .
1590 * We would use SHGetSpecialFolder path, but that wasn't added until IE4.
1592 if (!SUCCEEDED(SHGetSpecialFolderLocation(NULL, CSIDL_APPDATA,
1593 &idl))) {
1594 GetCurrentDirectory(MAX_PATH, path);
1595 is_set = 1;
1596 log_fn(LOG_WARN, "I couldn't find your application data folder: are you running an ancient version of Windows 95? Defaulting to '%s'", path);
1597 return path;
1599 /* Convert the path from an "ID List" (whatever that is!) to a path. */
1600 result = SHGetPathFromIDList(idl, path);
1601 /* Now we need to free the */
1602 SHGetMalloc(&m);
1603 if (m) {
1604 m->lpVtbl->Free(m, idl);
1605 m->lpVtbl->Release(m);
1607 if (!SUCCEEDED(result)) {
1608 return NULL;
1610 strlcat(path,"\\tor",MAX_PATH);
1611 is_set = 1;
1612 return path;
1614 #endif
1616 /** Return the default location for our torrc file. */
1617 static char *
1618 get_default_conf_file(void)
1620 #ifdef MS_WINDOWS
1621 char *path = tor_malloc(MAX_PATH);
1622 strlcpy(path, get_windows_conf_root(), MAX_PATH);
1623 strlcat(path,"\\torrc",MAX_PATH);
1624 return path;
1625 #else
1626 return tor_strdup(CONFDIR "/torrc");
1627 #endif
1630 /** Verify whether lst is a string containing valid-looking space-separated
1631 * nicknames, or NULL. Return 0 on success. Warn and return -1 on failure.
1633 static int check_nickname_list(const char *lst, const char *name)
1635 int r = 0;
1636 smartlist_t *sl;
1638 if (!lst)
1639 return 0;
1640 sl = smartlist_create();
1641 smartlist_split_string(sl, lst, ",", SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
1642 SMARTLIST_FOREACH(sl, const char *, s,
1644 if (!is_legal_nickname_or_hexdigest(s)) {
1645 log_fn(LOG_WARN, "Invalid nickname '%s' in %s line", s, name);
1646 r = -1;
1649 SMARTLIST_FOREACH(sl, char *, s, tor_free(s));
1650 smartlist_free(sl);
1651 return r;
1654 /** Read a configuration file into <b>options</b>, finding the configuration
1655 * file location based on the command line. After loading the options,
1656 * validate them for consistency, then take actions based on them.
1657 * Return 0 if success, -1 if failure. */
1659 init_from_config(int argc, char **argv)
1661 or_options_t *oldoptions, *newoptions;
1662 struct config_line_t *cl;
1663 char *cf=NULL, *fname=NULL;
1664 int i, retval;
1665 int using_default_torrc;
1666 static char **backup_argv;
1667 static int backup_argc;
1669 if (argv) { /* first time we're called. save commandline args */
1670 backup_argv = argv;
1671 backup_argc = argc;
1672 oldoptions = NULL;
1673 } else { /* we're reloading. need to clean up old options first. */
1674 argv = backup_argv;
1675 argc = backup_argc;
1676 oldoptions = get_options();
1678 if (argc > 1 && (!strcmp(argv[1], "-h") || !strcmp(argv[1],"--help"))) {
1679 print_usage();
1680 exit(0);
1683 if (argc > 1 && (!strcmp(argv[1],"--version"))) {
1684 printf("Tor version %s.\n",VERSION);
1685 if (argc > 2 && (!strcmp(argv[2],"--version"))) {
1686 print_cvs_version();
1688 exit(0);
1691 newoptions = tor_malloc_zero(sizeof(or_options_t));
1692 options_init(newoptions);
1694 /* learn config file name, get config lines, assign them */
1695 fname = NULL;
1696 using_default_torrc = 1;
1697 newoptions->command = CMD_RUN_TOR;
1698 for (i = 1; i < argc; ++i) {
1699 if (i < argc-1 && !strcmp(argv[i],"-f")) {
1700 if (fname) {
1701 log(LOG_WARN, "Duplicate -f options on command line.");
1702 tor_free(fname);
1704 fname = tor_strdup(argv[i+1]);
1705 using_default_torrc = 0;
1706 ++i;
1707 } else if (!strcmp(argv[i],"--list-fingerprint")) {
1708 newoptions->command = CMD_LIST_FINGERPRINT;
1709 } else if (!strcmp(argv[i],"--hash-password")) {
1710 newoptions->command = CMD_HASH_PASSWORD;
1711 newoptions->command_arg = tor_strdup( (i < argc-1) ? argv[i+1] : "");
1712 ++i;
1716 if (using_default_torrc) {
1717 /* didn't find one, try CONFDIR */
1718 char *fn;
1719 fn = get_default_conf_file();
1720 if (fn && file_status(fn) == FN_FILE) {
1721 fname = fn;
1722 } else {
1723 tor_free(fn);
1724 #ifndef MS_WINDOWS
1725 fn = expand_filename("~/.torrc");
1726 if (fn && file_status(fn) == FN_FILE) {
1727 fname = fn;
1728 } else {
1729 tor_free(fn);
1730 fname = get_default_conf_file();
1732 #else
1733 fname = get_default_conf_file();
1734 #endif
1737 tor_assert(fname);
1738 log(LOG_DEBUG, "Opening config file '%s'", fname);
1740 if (file_status(fname) != FN_FILE ||
1741 !(cf = read_file_to_str(fname,0))) {
1742 if (using_default_torrc == 1) {
1743 log(LOG_NOTICE, "Configuration file '%s' not present, "
1744 "using reasonable defaults.", fname);
1745 tor_free(fname); /* sets fname to NULL */
1746 } else {
1747 log(LOG_WARN, "Unable to open configuration file '%s'.", fname);
1748 tor_free(fname);
1749 goto err;
1751 } else { /* it opened successfully. use it. */
1752 retval = config_get_lines(cf, &cl);
1753 tor_free(cf);
1754 if (retval < 0)
1755 goto err;
1756 retval = config_assign(newoptions, cl, 0);
1757 config_free_lines(cl);
1758 if (retval < 0)
1759 goto err;
1762 /* Go through command-line variables too */
1763 cl = config_get_commandlines(argc,argv);
1764 retval = config_assign(newoptions,cl,0);
1765 config_free_lines(cl);
1766 if (retval < 0)
1767 goto err;
1769 /* Validate newoptions */
1770 if (options_validate(newoptions) < 0)
1771 goto err;
1773 if (options_transition_allowed(oldoptions, newoptions) < 0)
1774 goto err;
1776 set_options(newoptions); /* frees and replaces old options */
1777 if (options_act() < 0) { /* acting on them failed. die. */
1778 log_fn(LOG_ERR,"Acting on config options left us in a broken state. Dying.");
1779 exit(1);
1781 tor_free(config_fname);
1782 config_fname = fname;
1783 return 0;
1784 err:
1785 tor_free(fname);
1786 options_free(newoptions);
1787 return -1;
1790 /** If <b>range</b> is of the form MIN-MAX, for MIN and MAX both
1791 * recognized log severity levels, set *<b>min_out</b> to MIN and
1792 * *<b>max_out</b> to MAX and return 0. Else, if <b>range<b> is of
1793 * the form MIN, act as if MIN-err had been specified. Else, warn and
1794 * return -1.
1796 static int
1797 parse_log_severity_range(const char *range, int *min_out, int *max_out)
1799 int levelMin, levelMax;
1800 const char *cp;
1801 cp = strchr(range, '-');
1802 if (cp) {
1803 if (cp == range) {
1804 levelMin = LOG_DEBUG;
1805 } else {
1806 char *tmp_sev = tor_strndup(range, cp - range);
1807 levelMin = parse_log_level(tmp_sev);
1808 if (levelMin < 0) {
1809 log_fn(LOG_WARN, "Unrecognized log severity '%s': must be one of "
1810 "err|warn|notice|info|debug", tmp_sev);
1811 tor_free(tmp_sev);
1812 return -1;
1814 tor_free(tmp_sev);
1816 if (!*(cp+1)) {
1817 levelMax = LOG_ERR;
1818 } else {
1819 levelMax = parse_log_level(cp+1);
1820 if (levelMax < 0) {
1821 log_fn(LOG_WARN, "Unrecognized log severity '%s': must be one of "
1822 "err|warn|notice|info|debug", cp+1);
1823 return -1;
1826 } else {
1827 levelMin = parse_log_level(range);
1828 if (levelMin < 0) {
1829 log_fn(LOG_WARN, "Unrecognized log severity '%s': must be one of "
1830 "err|warn|notice|info|debug", range);
1831 return -1;
1833 levelMax = LOG_ERR;
1836 *min_out = levelMin;
1837 *max_out = levelMax;
1839 return 0;
1842 /** Try to convert a pair of old-style logging options [LogLevel, and
1843 * (LogFile/Syslog)] to a new-style option, and add the new option to
1844 * options->Logs. */
1845 static int
1846 convert_log_option(or_options_t *options, struct config_line_t *level_opt,
1847 struct config_line_t *file_opt, int isDaemon)
1849 int levelMin = -1, levelMax = -1;
1851 if (level_opt) {
1852 if (parse_log_severity_range(level_opt->value, &levelMin, &levelMax))
1853 return -1;
1855 if (levelMin < 0 && levelMax < 0) {
1856 levelMin = LOG_NOTICE;
1857 levelMax = LOG_ERR;
1858 } else if (levelMin < 0) {
1859 levelMin = levelMax;
1860 } else {
1861 levelMax = LOG_ERR;
1864 if (file_opt && !strcasecmp(file_opt->key, "LogFile")) {
1865 if (add_single_log_option(options, levelMin, levelMax, "file", file_opt->value) < 0) {
1866 log_fn(LOG_WARN, "Cannot write to LogFile '%s': %s.", file_opt->value,
1867 strerror(errno));
1868 return -1;
1870 } else if (file_opt && !strcasecmp(file_opt->key, "SysLog")) {
1871 if (add_single_log_option(options, levelMin, levelMax, "syslog", NULL) < 0)
1872 return -1;
1873 } else if (!isDaemon) {
1874 add_single_log_option(options, levelMin, levelMax, "stdout", NULL);
1876 return 0;
1880 * Initialize the logs based on the configuration file.
1883 config_init_logs(or_options_t *options, int validate_only)
1885 struct config_line_t *opt;
1886 int ok;
1887 smartlist_t *elts;
1889 ok = 1;
1890 elts = smartlist_create();
1891 for (opt = options->Logs; opt; opt = opt->next) {
1892 int levelMin=LOG_DEBUG, levelMax=LOG_ERR;
1893 smartlist_split_string(elts, opt->value, NULL,
1894 SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 3);
1895 if (smartlist_len(elts) == 0) {
1896 log_fn(LOG_WARN, "Bad syntax on Log option 'Log %s'", opt->value);
1897 ok = 0; goto cleanup;
1899 if (parse_log_severity_range(smartlist_get(elts,0), &levelMin, &levelMax)) {
1900 ok = 0; goto cleanup;
1902 if (smartlist_len(elts) < 2) { /* only loglevels were provided */
1903 if (!validate_only)
1904 add_stream_log(levelMin, levelMax, "<stdout>", stdout);
1905 goto cleanup;
1907 if (!strcasecmp(smartlist_get(elts,1), "file")) {
1908 if (smartlist_len(elts) != 3) {
1909 log_fn(LOG_WARN, "Bad syntax on Log option 'Log %s'", opt->value);
1910 ok = 0; goto cleanup;
1912 if (!validate_only)
1913 add_file_log(levelMin, levelMax, smartlist_get(elts, 2));
1914 goto cleanup;
1916 if (smartlist_len(elts) != 2) {
1917 log_fn(LOG_WARN, "Bad syntax on Log option 'Log %s'", opt->value);
1918 ok = 0; goto cleanup;
1920 if (!strcasecmp(smartlist_get(elts,1), "stdout")) {
1921 if (!validate_only) {
1922 add_stream_log(levelMin, levelMax, "<stdout>", stdout);
1923 close_temp_logs();
1925 } else if (!strcasecmp(smartlist_get(elts,1), "stderr")) {
1926 if (!validate_only) {
1927 add_stream_log(levelMin, levelMax, "<stderr>", stderr);
1928 close_temp_logs();
1930 } else if (!strcasecmp(smartlist_get(elts,1), "syslog")) {
1931 #ifdef HAVE_SYSLOG_H
1932 if (!validate_only)
1933 add_syslog_log(levelMin, levelMax);
1934 #else
1935 log_fn(LOG_WARN, "Syslog is not supported in this compilation.");
1936 #endif
1937 } else {
1938 log_fn(LOG_WARN, "Unrecognized log type %s",
1939 (const char*)smartlist_get(elts,1));
1940 if (strchr(smartlist_get(elts,1), '/')) {
1941 log_fn(LOG_WARN, "Did you mean to say 'Log file %s' ?",
1942 (const char *)smartlist_get(elts,1));
1944 ok = 0; goto cleanup;
1946 cleanup:
1947 SMARTLIST_FOREACH(elts, char*, cp, tor_free(cp));
1948 smartlist_clear(elts);
1950 smartlist_free(elts);
1951 if (!validate_only)
1952 close_temp_logs();
1954 return ok?0:-1;
1957 /** Add a single option of the form Log min-max <type> [fname] to options. */
1958 static int
1959 add_single_log_option(or_options_t *options, int minSeverity, int maxSeverity,
1960 const char *type, const char *fname)
1962 char buf[512];
1963 int n;
1965 n = tor_snprintf(buf, sizeof(buf), "%s%s%s %s%s%s",
1966 log_level_to_string(minSeverity),
1967 maxSeverity == LOG_ERR ? "" : "-",
1968 maxSeverity == LOG_ERR ? "" : log_level_to_string(maxSeverity),
1969 type, fname?" ":"", fname?fname:"");
1970 if (n<0) {
1971 log_fn(LOG_WARN, "Normalized log option too long.");
1972 return -1;
1975 log(LOG_WARN, "The old LogLevel/LogFile/DebugLogFile/SysLog options are deprecated, and will go away soon. Your new torrc line should be: 'Log %s'", buf);
1976 config_line_append(&options->Logs, "Log", buf);
1977 return 0;
1980 /** Convert all old-style logging options to new-style Log options. Return 0
1981 * on success, -1 on failure. */
1982 static int
1983 normalize_log_options(or_options_t *options)
1985 /* The order of options is: Level? (File Level?)+
1987 struct config_line_t *opt = options->OldLogOptions;
1989 /* Special case for if first option is LogLevel. */
1990 if (opt && !strcasecmp(opt->key, "LogLevel")) {
1991 if (opt->next && (!strcasecmp(opt->next->key, "LogFile") ||
1992 !strcasecmp(opt->next->key, "SysLog"))) {
1993 if (convert_log_option(options, opt, opt->next, options->RunAsDaemon) < 0)
1994 return -1;
1995 opt = opt->next->next;
1996 } else if (!opt->next) {
1997 if (convert_log_option(options, opt, NULL, options->RunAsDaemon) < 0)
1998 return -1;
1999 opt = opt->next;
2000 } else {
2001 ; /* give warning below */
2005 while (opt) {
2006 if (!strcasecmp(opt->key, "LogLevel")) {
2007 log_fn(LOG_WARN, "Two LogLevel options in a row without intervening LogFile or SysLog");
2008 opt = opt->next;
2009 } else {
2010 tor_assert(!strcasecmp(opt->key, "LogFile") ||
2011 !strcasecmp(opt->key, "SysLog"));
2012 if (opt->next && !strcasecmp(opt->next->key, "LogLevel")) {
2013 /* LogFile/SysLog followed by LogLevel */
2014 if (convert_log_option(options,opt->next,opt, options->RunAsDaemon) < 0)
2015 return -1;
2016 opt = opt->next->next;
2017 } else {
2018 /* LogFile/SysLog followed by LogFile/SysLog or end of list. */
2019 if (convert_log_option(options,NULL, opt, options->RunAsDaemon) < 0)
2020 return -1;
2021 opt = opt->next;
2026 if (options->DebugLogFile) {
2027 if (add_single_log_option(options, LOG_DEBUG, LOG_ERR, "file", options->DebugLogFile) < 0)
2028 return -1;
2031 tor_free(options->DebugLogFile);
2032 config_free_lines(options->OldLogOptions);
2033 options->OldLogOptions = NULL;
2035 return 0;
2039 * Given a linked list of config lines containing "allow" and "deny" tokens,
2040 * parse them and append the result to <b>dest</b>. Return -1 if any tokens
2041 * are malformed, else return 0.
2044 config_parse_addr_policy(struct config_line_t *cfg,
2045 addr_policy_t **dest)
2047 addr_policy_t **nextp;
2048 smartlist_t *entries;
2049 int r = 0;
2051 if (!cfg)
2052 return 0;
2054 nextp = dest;
2056 while (*nextp)
2057 nextp = &((*nextp)->next);
2059 entries = smartlist_create();
2060 for (; cfg; cfg = cfg->next) {
2061 smartlist_split_string(entries, cfg->value, ",", SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
2062 SMARTLIST_FOREACH(entries, const char *, ent,
2064 log_fn(LOG_DEBUG,"Adding new entry '%s'",ent);
2065 *nextp = router_parse_addr_policy_from_string(ent);
2066 if (*nextp) {
2067 nextp = &((*nextp)->next);
2068 } else {
2069 log_fn(LOG_WARN,"Malformed policy %s.", ent);
2070 r = -1;
2073 SMARTLIST_FOREACH(entries, char *, ent, tor_free(ent));
2074 smartlist_clear(entries);
2076 smartlist_free(entries);
2077 return r;
2080 /** Release all storage held by <b>p</b> */
2081 void
2082 addr_policy_free(addr_policy_t *p) {
2083 addr_policy_t *e;
2085 while (p) {
2086 e = p;
2087 p = p->next;
2088 tor_free(e->string);
2089 tor_free(e);
2093 /** Parse a single RedirectExit line's contents from <b>line</b>. If
2094 * they are valid, and <b>result</b> is not NULL, add an element to
2095 * <b>result</b> and return 0. Else if they are valid, return 0.
2096 * Else return -1. */
2097 static int
2098 parse_redirect_line(smartlist_t *result, struct config_line_t *line)
2100 smartlist_t *elements = NULL;
2101 exit_redirect_t *r;
2103 tor_assert(line);
2105 r = tor_malloc_zero(sizeof(exit_redirect_t));
2106 elements = smartlist_create();
2107 smartlist_split_string(elements, line->value, NULL,
2108 SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
2109 if (smartlist_len(elements) != 2) {
2110 log_fn(LOG_WARN, "Wrong number of elements in RedirectExit line");
2111 goto err;
2113 if (parse_addr_and_port_range(smartlist_get(elements,0),&r->addr,&r->mask,
2114 &r->port_min,&r->port_max)) {
2115 log_fn(LOG_WARN, "Error parsing source address in RedirectExit line");
2116 goto err;
2118 if (0==strcasecmp(smartlist_get(elements,1), "pass")) {
2119 r->is_redirect = 0;
2120 } else {
2121 if (parse_addr_port(smartlist_get(elements,1),NULL,&r->addr_dest,
2122 &r->port_dest)) {
2123 log_fn(LOG_WARN, "Error parsing dest address in RedirectExit line");
2124 goto err;
2126 r->is_redirect = 1;
2129 goto done;
2130 err:
2131 tor_free(r);
2132 done:
2133 SMARTLIST_FOREACH(elements, char *, cp, tor_free(cp));
2134 smartlist_free(elements);
2135 if (r) {
2136 if (result)
2137 smartlist_add(result, r);
2138 else
2139 tor_free(r);
2140 return 0;
2141 } else {
2142 return -1;
2146 /** Read the contents of a DirServer line from <b>line</b>. Return 0
2147 * if the line is well-formed, and 0 if it isn't. If
2148 * <b>validate_only</b> is 0, and the line is well-formed, then add
2149 * the dirserver described in the line as a valid server. */
2150 static int
2151 parse_dir_server_line(const char *line, int validate_only)
2153 smartlist_t *items = NULL;
2154 int r;
2155 char *addrport, *address=NULL;
2156 uint16_t port;
2157 char digest[DIGEST_LEN];
2159 items = smartlist_create();
2160 smartlist_split_string(items, line, NULL,
2161 SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 2);
2162 if (smartlist_len(items) < 2) {
2163 log_fn(LOG_WARN, "Too few arguments to DirServer line.");
2164 goto err;
2166 addrport = smartlist_get(items, 0);
2167 if (parse_addr_port(addrport, &address, NULL, &port)<0) {
2168 log_fn(LOG_WARN, "Error parsing DirServer address '%s'", addrport);
2169 goto err;
2171 if (!port) {
2172 log_fn(LOG_WARN, "Missing port in DirServer address '%s'",addrport);
2173 goto err;
2176 tor_strstrip(smartlist_get(items, 1), " ");
2177 if (strlen(smartlist_get(items, 1)) != HEX_DIGEST_LEN) {
2178 log_fn(LOG_WARN, "Key digest for DirServer is wrong length.");
2179 goto err;
2181 if (base16_decode(digest, DIGEST_LEN,
2182 smartlist_get(items,1), HEX_DIGEST_LEN)<0) {
2183 log_fn(LOG_WARN, "Unable to decode DirServer key digest.");
2184 goto err;
2187 if (!validate_only) {
2188 log_fn(LOG_DEBUG, "Trusted dirserver at %s:%d (%s)", address, (int)port,
2189 (char*)smartlist_get(items,1));
2190 add_trusted_dir_server(address, port, digest);
2193 r = 0;
2194 goto done;
2196 err:
2197 r = -1;
2199 done:
2200 SMARTLIST_FOREACH(items, char*, s, tor_free(s));
2201 smartlist_free(items);
2202 tor_free(address);
2203 return r;
2206 /** Adjust the value of options->DataDirectory, or fill it in if it's
2207 * absent. Return 0 on success, -1 on failure. */
2208 static int
2209 normalize_data_directory(or_options_t *options) {
2210 #ifdef MS_WINDOWS
2211 char *p;
2212 if (options->DataDirectory)
2213 return 0; /* all set */
2214 p = tor_malloc(MAX_PATH);
2215 strlcpy(p,get_windows_conf_root(),MAX_PATH);
2216 options->DataDirectory = p;
2217 return 0;
2218 #else
2219 const char *d = options->DataDirectory;
2220 if (!d)
2221 d = "~/.tor";
2223 if (strncmp(d,"~/",2) == 0) {
2224 char *fn = expand_filename(d);
2225 if (!fn) {
2226 log_fn(LOG_ERR,"Failed to expand filename '%s'.", d);
2227 return -1;
2229 if (!options->DataDirectory && !strcmp(fn,"/.tor")) {
2230 /* If our homedir is /, we probably don't want to use it. */
2231 /* XXXX Default to /var/lib/tor? */
2232 log_fn(LOG_WARN, "Defaulting to 'DataDirectory %s', which may not be what you want", fn);
2234 tor_free(options->DataDirectory);
2235 options->DataDirectory = fn;
2237 return 0;
2238 #endif
2241 /** Check and normalize the value of options->DataDirectory; return 0 if it
2242 * sane, -1 otherwise. */
2243 static int
2244 validate_data_directory(or_options_t *options) {
2245 if (normalize_data_directory(options) < 0)
2246 return -1;
2247 tor_assert(options->DataDirectory);
2248 if (strlen(options->DataDirectory) > (512-128)) {
2249 log_fn(LOG_ERR, "DataDirectory is too long.");
2250 return -1;
2252 #if 0
2253 if (check_private_dir(options->DataDirectory, CPD_CHECK != 0)) {
2254 log_fn(LOG_WARN, "Can't create directory %s", options->DataDirectory);
2255 return -1;
2257 #endif
2258 return 0;
2261 #define GENERATED_FILE_PREFIX "# This file was generated by Tor; if you edit it, comments will not be preserved"
2263 /** Save a configuration file for the configuration in <b>options</b>
2264 * into the file <b>fname</b>. If the file already exists, and
2265 * doesn't begin with GENERATED_FILE_PREFIX, rename it. Otherwise
2266 * replace it. Return 0 on success, -1 on failure. */
2267 static int
2268 write_configuration_file(const char *fname, or_options_t *options)
2270 char fn_tmp[1024];
2271 char *old_val=NULL, *new_val=NULL, *new_conf=NULL;
2272 int rename_old = 0, r;
2273 size_t len;
2275 if (fname) {
2276 switch (file_status(fname)) {
2277 case FN_FILE:
2278 old_val = read_file_to_str(fname, 0);
2279 if (strcmpstart(old_val, GENERATED_FILE_PREFIX)) {
2280 rename_old = 1;
2282 tor_free(old_val);
2283 break;
2284 case FN_NOENT:
2285 break;
2286 default:
2287 log_fn(LOG_WARN,"Config file %s is not a file? Failing.", fname);
2288 return -1;
2292 if (!(new_conf = config_dump_options(options, 1))) {
2293 log_fn(LOG_WARN, "Couldn't get configuration string");
2294 goto err;
2297 len = strlen(new_conf)+128;
2298 new_val = tor_malloc(len);
2299 tor_snprintf(new_val, len, "%s\n\n%s", GENERATED_FILE_PREFIX, new_conf);
2301 if (rename_old) {
2302 int i = 1;
2303 while (1) {
2304 if (tor_snprintf(fn_tmp, sizeof(fn_tmp), "%s.orig.%d", fname, i)<0) {
2305 log_fn(LOG_WARN, "Filename too long");
2306 goto err;
2308 if (file_status(fn_tmp) == FN_NOENT)
2309 break;
2310 ++i;
2312 log_fn(LOG_NOTICE, "Renaming old configuration file to %s", fn_tmp);
2313 rename(fname, fn_tmp);
2316 write_str_to_file(fname, new_val, 0);
2318 r = 0;
2319 goto done;
2320 err:
2321 r = -1;
2322 done:
2323 tor_free(new_val);
2324 tor_free(new_conf);
2325 return r;
2329 * Save the current configuration file value to disk. Return 0 on
2330 * success, -1 on failure.
2333 save_current_config(void)
2335 char *fn;
2336 if (config_fname) {
2337 /* XXX This fails if we can't write to our configuration file.
2338 * Arguably, we should try falling back to datadirectory or something.
2339 * But just as arguably, we shouldn't. */
2340 return write_configuration_file(config_fname, get_options());
2342 fn = get_default_conf_file();
2343 return write_configuration_file(fn, get_options());
2346 struct unit_table_t {
2347 const char *unit;
2348 uint64_t multiplier;
2351 static struct unit_table_t memory_units[] = {
2352 { "", 1 },
2353 { "b", 1<< 0 },
2354 { "byte", 1<< 0 },
2355 { "bytes", 1<< 0 },
2356 { "kb", 1<<10 },
2357 { "kilobyte", 1<<10 },
2358 { "kilobytes", 1<<10 },
2359 { "m", 1<<20 },
2360 { "mb", 1<<20 },
2361 { "megabyte", 1<<20 },
2362 { "megabytes", 1<<20 },
2363 { "gb", 1<<30 },
2364 { "gigabyte", 1<<30 },
2365 { "gigabytes", 1<<30 },
2366 { "tb", U64_LITERAL(1)<<40 },
2367 { "terabyte", U64_LITERAL(1)<<40 },
2368 { "terabytes", U64_LITERAL(1)<<40 },
2369 { NULL, 0 },
2372 static struct unit_table_t time_units[] = {
2373 { "", 1 },
2374 { "second", 1 },
2375 { "seconds", 1 },
2376 { "minute", 60 },
2377 { "minutes", 60 },
2378 { "hour", 60*60 },
2379 { "hours", 60*60 },
2380 { "day", 24*60*60 },
2381 { "days", 24*60*60 },
2382 { "week", 7*24*60*60 },
2383 { "weeks", 7*24*60*60 },
2384 { NULL, 0 },
2387 /** Parse a string <b>val</b> containing a number, zero or more
2388 * spaces, and an optional unit string. If the unit appears in the
2389 * table <b>u</b>, then multiply the number by the unit multiplier.
2390 * On success, set *<b>ok</b> to 1 and return this product.
2391 * Otherwise, set *<b>ok</b> to 0.
2393 static uint64_t
2394 config_parse_units(const char *val, struct unit_table_t *u, int *ok)
2396 uint64_t v;
2397 char *cp;
2399 tor_assert(ok);
2401 v = tor_parse_uint64(val, 10, 0, UINT64_MAX, ok, &cp);
2402 if (!*ok)
2403 return 0;
2404 if (!cp) {
2405 *ok = 1;
2406 return v;
2408 while (TOR_ISSPACE(*cp))
2409 ++cp;
2410 for ( ;u->unit;++u) {
2411 if (!strcasecmp(u->unit, cp)) {
2412 v *= u->multiplier;
2413 *ok = 1;
2414 return v;
2417 log_fn(LOG_WARN, "Unknown unit '%s'.", cp);
2418 *ok = 0;
2419 return 0;
2422 /** Parse a string in the format "number unit", where unit is a unit of
2423 * information (byte, KB, M, etc). On success, set *<b>ok</b> to true
2424 * and return the number of bytes specified. Otherwise, set
2425 * *<b>ok</b> to false and return 0. */
2426 static uint64_t
2427 config_parse_memunit(const char *s, int *ok) {
2428 return config_parse_units(s, memory_units, ok);
2431 /** Parse a string in the format "number unit", where unit is a unit of time.
2432 * On success, set *<b>ok</b> to true and return the number of seconds in
2433 * the provided interval. Otherwise, set *<b>ok</b> to 0 and return -1.
2435 static int
2436 config_parse_interval(const char *s, int *ok) {
2437 uint64_t r;
2438 r = config_parse_units(s, time_units, ok);
2439 if (!ok)
2440 return -1;
2441 if (r > INT_MAX) {
2442 log_fn(LOG_WARN, "Interval '%s' is too long", s);
2443 *ok = 0;
2444 return -1;
2446 return (int)r;
2449 static void
2450 print_cvs_version(void)
2452 extern const char aes_c_id[];
2453 extern const char compat_c_id[];
2454 extern const char container_c_id[];
2455 extern const char crypto_c_id[];
2456 extern const char log_c_id[];
2457 extern const char torgzip_c_id[];
2458 extern const char tortls_c_id[];
2459 extern const char util_c_id[];
2461 extern const char buffers_c_id[];
2462 extern const char circuitbuild_c_id[];
2463 extern const char circuitlist_c_id[];
2464 extern const char circuituse_c_id[];
2465 extern const char command_c_id[];
2466 // extern const char config_c_id[];
2467 extern const char connection_c_id[];
2468 extern const char connection_edge_c_id[];
2469 extern const char connection_or_c_id[];
2470 extern const char control_c_id[];
2471 extern const char cpuworker_c_id[];
2472 extern const char directory_c_id[];
2473 extern const char dirserv_c_id[];
2474 extern const char dns_c_id[];
2475 extern const char hibernate_c_id[];
2476 extern const char main_c_id[];
2477 extern const char onion_c_id[];
2478 extern const char relay_c_id[];
2479 extern const char rendclient_c_id[];
2480 extern const char rendcommon_c_id[];
2481 extern const char rendmid_c_id[];
2482 extern const char rendservice_c_id[];
2483 extern const char rephist_c_id[];
2484 extern const char router_c_id[];
2485 extern const char routerlist_c_id[];
2486 extern const char routerparse_c_id[];
2488 puts(AES_H_ID);
2489 puts(COMPAT_H_ID);
2490 puts(CONTAINER_H_ID);
2491 puts(CRYPTO_H_ID);
2492 puts(LOG_H_ID);
2493 puts(TORGZIP_H_ID);
2494 puts(TORINT_H_ID);
2495 puts(TORTLS_H_ID);
2496 puts(UTIL_H_ID);
2497 puts(aes_c_id);
2498 puts(compat_c_id);
2499 puts(container_c_id);
2500 puts(crypto_c_id);
2501 puts(log_c_id);
2502 puts(torgzip_c_id);
2503 puts(tortls_c_id);
2504 puts(util_c_id);
2506 puts(OR_H_ID);
2507 puts(buffers_c_id);
2508 puts(circuitbuild_c_id);
2509 puts(circuitlist_c_id);
2510 puts(circuituse_c_id);
2511 puts(command_c_id);
2512 puts(config_c_id);
2513 puts(connection_c_id);
2514 puts(connection_edge_c_id);
2515 puts(connection_or_c_id);
2516 puts(control_c_id);
2517 puts(cpuworker_c_id);
2518 puts(directory_c_id);
2519 puts(dirserv_c_id);
2520 puts(dns_c_id);
2521 puts(hibernate_c_id);
2522 puts(main_c_id);
2523 puts(onion_c_id);
2524 puts(relay_c_id);
2525 puts(rendclient_c_id);
2526 puts(rendcommon_c_id);
2527 puts(rendmid_c_id);
2528 puts(rendservice_c_id);
2529 puts(rephist_c_id);
2530 puts(router_c_id);
2531 puts(routerlist_c_id);
2532 puts(routerparse_c_id);