dns.c 71.4 KB
Newer Older
1
2
/* Copyright (c) 2003-2004, Roger Dingledine.
 * Copyright (c) 2004-2006, Roger Dingledine, Nick Mathewson.
3
 * Copyright (c) 2007-2012, The Tor Project, Inc. */
4
5
/* See LICENSE for licensing information */

Roger Dingledine's avatar
Roger Dingledine committed
6
7
/**
 * \file dns.c
8
 * \brief Implements a local cache for DNS results for Tor servers.
Roger Dingledine's avatar
Roger Dingledine committed
9
 * This is implemented as a wrapper around Adam Langley's eventdns.c code.
10
11
 * (We can't just use gethostbyname() and friends because we really need to
 * be nonblocking.)
Roger Dingledine's avatar
Roger Dingledine committed
12
 **/
13

14
#include "or.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
15
#include "circuitlist.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
16
#include "circuituse.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
17
#include "config.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
18
#include "connection.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
19
#include "connection_edge.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
20
#include "control.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
21
#include "dns.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
22
#include "main.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
23
#include "policies.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
24
#include "relay.h"
Sebastian Hahn's avatar
Sebastian Hahn committed
25
#include "router.h"
26
#include "ht.h"
27
#ifdef HAVE_EVENT2_DNS_H
28
#include <event2/event.h>
29
30
#include <event2/dns.h>
#else
31
#include <event.h>
32
#include "eventdns.h"
33
34
35
36
#ifndef HAVE_EVDNS_SET_DEFAULT_OUTGOING_BIND_ADDRESS
#define HAVE_EVDNS_SET_DEFAULT_OUTGOING_BIND_ADDRESS
#endif
#endif
37

38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
#ifndef HAVE_EVENT2_DNS_H
struct evdns_base;
struct evdns_request;
#define evdns_base_new(x,y) tor_malloc(1)
#define evdns_base_clear_nameservers_and_suspend(base) \
  evdns_clear_nameservers_and_suspend()
#define evdns_base_search_clear(base) evdns_search_clear()
#define evdns_base_set_default_outgoing_bind_address(base, a, len)  \
  evdns_set_default_outgoing_bind_address((a),(len))
#define evdns_base_resolv_conf_parse(base, options, fname) \
  evdns_resolv_conf_parse((options), (fname))
#define evdns_base_count_nameservers(base)      \
  evdns_count_nameservers()
#define evdns_base_resume(base)                 \
  evdns_resume()
#define evdns_base_config_windows_nameservers(base)     \
  evdns_config_windows_nameservers()
55
56
#define evdns_base_set_option_(base, opt, val) \
  evdns_set_option((opt),(val),DNS_OPTIONS_ALL)
57
/* Note: our internal eventdns.c, plus Libevent 1.4, used a 1 return to
58
 * signify failure to launch a resolve. Libevent 2.0 uses a -1 return to
59
 * signify a failure on a resolve, though if we're on Libevent 2.0, we should
60
 * have event2/dns.h and never hit these macros.  Regardless, 0 is success. */
61
#define evdns_base_resolve_ipv4(base, addr, options, cb, ptr) \
62
63
  ((evdns_resolve_ipv4((addr), (options), (cb), (ptr))!=0)    \
   ? NULL : ((void*)1))
64
65
66
#define evdns_base_resolve_ipv6(base, addr, options, cb, ptr) \
  ((evdns_resolve_ipv6((addr), (options), (cb), (ptr))!=0)    \
   ? NULL : ((void*)1))
67
68
69
70
71
72
#define evdns_base_resolve_reverse(base, addr, options, cb, ptr)        \
  ((evdns_resolve_reverse((addr), (options), (cb), (ptr))!=0)           \
   ? NULL : ((void*)1))
#define evdns_base_resolve_reverse_ipv6(base, addr, options, cb, ptr)   \
  ((evdns_resolve_reverse_ipv6((addr), (options), (cb), (ptr))!=0)      \
   ? NULL : ((void*)1))
73
74
75
76
77
78
79
80

#elif defined(LIBEVENT_VERSION_NUMBER) && LIBEVENT_VERSION_NUMBER < 0x02000303
#define evdns_base_set_option_(base, opt, val) \
  evdns_base_set_option((base), (opt),(val),DNS_OPTIONS_ALL)

#else
#define evdns_base_set_option_ evdns_base_set_option

81
82
#endif

Roger Dingledine's avatar
Roger Dingledine committed
83
/** Longest hostname we're willing to resolve. */
84
85
#define MAX_ADDRESSLEN 256

86
87
/** How long will we wait for an answer from the resolver before we decide
 * that the resolver is wedged? */
88
89
#define RESOLVE_MAX_TIMEOUT 300

90
91
92
/** Our evdns_base; this structure handles all our name lookups. */
static struct evdns_base *the_evdns_base = NULL;

93
94
/** Have we currently configured nameservers with eventdns? */
static int nameservers_configured = 0;
95
96
/** Did our most recent attempt to configure nameservers with eventdns fail? */
static int nameserver_config_failed = 0;
97
98
99
100
101
102
/** What was the resolv_conf fname we last used when configuring the
 * nameservers? Used to check whether we need to reconfigure. */
static char *resolv_conf_fname = NULL;
/** What was the mtime on the resolv.conf file we last used when configuring
 * the nameservers?  Used to check whether we need to reconfigure. */
static time_t resolv_conf_mtime = 0;
103

Roger Dingledine's avatar
Roger Dingledine committed
104
/** Linked list of connections waiting for a DNS answer. */
105
typedef struct pending_connection_t {
106
  edge_connection_t *conn;
107
  struct pending_connection_t *next;
108
} pending_connection_t;
109

110
111
/** Value of 'magic' field for cached_resolve_t.  Used to try to catch bad
 * pointers and memory stomping. */
112
113
#define CACHED_RESOLVE_MAGIC 0x1234F00D

114
115
116
/* Possible states for a cached resolve_t */
/** We are waiting for the resolver system to tell us an answer here.
 * When we get one, or when we time out, the state of this cached_resolve_t
117
 * will become "DONE" and we'll possibly add a CACHED
118
119
120
 * entry. This cached_resolve_t will be in the hash table so that we will
 * know not to launch more requests for this addr, but rather to add more
 * connections to the pending list for the addr. */
121
#define CACHE_STATE_PENDING 0
122
123
124
/** This used to be a pending cached_resolve_t, and we got an answer for it.
 * Now we're waiting for this cached_resolve_t to expire.  This should
 * have no pending connections, and should not appear in the hash table. */
125
#define CACHE_STATE_DONE 1
126
127
/** We are caching an answer for this address. This should have no pending
 * connections, and should appear in the hash table. */
128
129
130
131
132
133
#define CACHE_STATE_CACHED 2

/* DOCDOC */
#define RES_STATUS_INFLIGHT 1
#define RES_STATUS_DONE_OK 2
#define RES_STATUS_DONE_ERR 3
134

Roger Dingledine's avatar
Roger Dingledine committed
135
/** A DNS request: possibly completed, possibly pending; cached_resolve
136
 * structs are stored at the OR side in a hash table, and as a linked
137
138
 * list from oldest to newest.
 */
139
typedef struct cached_resolve_t {
140
  HT_ENTRY(cached_resolve_t) node;
141
  uint32_t magic;
142
  char address[MAX_ADDRESSLEN]; /**< The hostname to be resolved. */
143
144
145
146
147

  union {
    uint32_t addr_ipv4; /**< IPv4 addr for <b>address</b>. */
    int err_ipv4;
  } result_ipv4;
148
  union {
149
150
151
152
153
154
155
156
157
158
159
160
161
    struct in6_addr addr_ipv6;
    int err_ipv6;
  } result_ipv6;
  union {
    char *hostname;
    int err_hostname;
  } result_ptr;
  unsigned int res_status_ipv4 : 2;
  unsigned int res_status_ipv6 : 2;
  unsigned int res_status_hostname : 2;

  uint8_t state; /**< Is this cached entry pending/done/informative? */
  //uint8_t is_reverse; /**< Is this a reverse (addr-to-hostname) lookup? */
162
  time_t expire; /**< Remove items from cache after this time. */
163
164
165
  uint32_t ttl_ipv4; /**< What TTL did the nameserver tell us? */
  uint32_t ttl_ipv6; /**< What TTL did the nameserver tell us? */
  uint32_t ttl_hostname; /**< What TTL did the nameserver tell us? */
166
  /** Connections that want to know when we get an answer for this resolve. */
167
  pending_connection_t *pending_connections;
168
169
  /** Position of this element in the heap*/
  int minheap_idx;
170
} cached_resolve_t;
171

172
static void purge_expired_resolves(time_t now);
173
174
175
176
static void dns_found_answer(const char *address, uint8_t query_type,
                             int dns_answer,
                             const tor_addr_t *addr,
                             const char *hostname,
177
                             uint32_t ttl);
178
static void send_resolved_cell(edge_connection_t *conn, uint8_t answer_type);
179
static int launch_resolve(cached_resolve_t *resolve);
180
static void add_wildcarded_test_address(const char *address);
181
static int configure_nameservers(int force);
182
static int answer_is_wildcarded(const char *ip);
183
static int dns_resolve_impl(edge_connection_t *exitconn, int is_resolve,
184
185
                            or_circuit_t *oncirc, char **resolved_to_hostname,
                            int *made_connection_pending_out);
186
187
188
189
190
191
192
static int set_exitconn_info_from_resolve(edge_connection_t *exitconn,
                                          const cached_resolve_t *resolve,
                                          char **hostname_out);
static int evdns_err_is_transient(int err);
static void inform_pending_connections(cached_resolve_t *resolve);
static void make_pending_resolve_cached(cached_resolve_t *cached);

193
#ifdef DEBUG_DNS_CACHE
194
195
static void assert_cache_ok_(void);
#define assert_cache_ok() assert_cache_ok_()
196
#else
197
#define assert_cache_ok() STMT_NIL
198
#endif
199
static void assert_resolve_ok(cached_resolve_t *resolve);
200

201
202
/** Hash table of cached_resolve objects. */
static HT_HEAD(cache_map, cached_resolve_t) cache_root;
203

204
205
206
207
208
/*DOCDOC*/
static uint64_t n_ipv6_requests_made = 0;
static uint64_t n_ipv6_timeouts = 0;
static int dns_is_broken_for_ipv6 = 0;

Roger Dingledine's avatar
Roger Dingledine committed
209
/** Function to compare hashed resolves on their addresses; used to
210
 * implement hash tables. */
211
212
static INLINE int
cached_resolves_eq(cached_resolve_t *a, cached_resolve_t *b)
213
{
214
  /* make this smarter one day? */
215
  assert_resolve_ok(a); // Not b; b may be just a search.
216
217
218
  return !strncmp(a->address, b->address, MAX_ADDRESSLEN);
}

219
/** Hash function for cached_resolve objects */
220
221
222
223
static INLINE unsigned int
cached_resolve_hash(cached_resolve_t *a)
{
  return ht_string_hash(a->address);
224
225
}

226
HT_PROTOTYPE(cache_map, cached_resolve_t, node, cached_resolve_hash,
227
             cached_resolves_eq)
228
HT_GENERATE(cache_map, cached_resolve_t, node, cached_resolve_hash,
229
            cached_resolves_eq, 0.6, malloc, realloc, free)
230

231
/** Initialize the DNS cache. */
232
static void
233
init_cache_map(void)
234
{
235
  HT_INIT(cache_map, &cache_root);
236
237
}

238
/** Helper: called by eventdns when eventdns wants to log something. */
239
static void
240
evdns_log_cb(int warn, const char *msg)
241
{
242
  const char *cp;
243
244
  static int all_down = 0;
  int severity = warn ? LOG_WARN : LOG_INFO;
245
246
247
248
  if (!strcmpstart(msg, "Resolve requested for") &&
      get_options()->SafeLogging) {
    log(LOG_INFO, LD_EXIT, "eventdns: Resolve requested.");
    return;
249
250
  } else if (!strcmpstart(msg, "Search: ")) {
    return;
251
  }
252
253
  if (!strcmpstart(msg, "Nameserver ") && (cp=strstr(msg, " has failed: "))) {
    char *ns = tor_strndup(msg+11, cp-(msg+11));
254
    const char *err = strchr(cp, ':')+2;
255
    tor_assert(err);
256
257
258
    /* Don't warn about a single failed nameserver; we'll warn with 'all
     * nameservers have failed' if we're completely out of nameservers;
     * otherwise, the situation is tolerable. */
259
    severity = LOG_INFO;
260
    control_event_server_status(LOG_NOTICE,
261
262
263
264
265
266
                                "NAMESERVER_STATUS NS=%s STATUS=DOWN ERR=%s",
                                ns, escaped(err));
    tor_free(ns);
  } else if (!strcmpstart(msg, "Nameserver ") &&
             (cp=strstr(msg, " is back up"))) {
    char *ns = tor_strndup(msg+11, cp-(msg+11));
267
    severity = (all_down && warn) ? LOG_NOTICE : LOG_INFO;
268
    all_down = 0;
269
270
271
272
273
    control_event_server_status(LOG_NOTICE,
                                "NAMESERVER_STATUS NS=%s STATUS=UP", ns);
    tor_free(ns);
  } else if (!strcmp(msg, "All nameservers have failed")) {
    control_event_server_status(LOG_WARN, "NAMESERVER_ALL_DOWN");
274
    all_down = 1;
275
  }
276
  log(severity, LD_EXIT, "eventdns: %s", msg);
277
278
}

279
280
/** Helper: passed to eventdns.c as a callback so it can generate random
 * numbers for transaction IDs and 0x20-hack coding. */
281
static void
282
dns_randfn_(char *b, size_t n)
283
{
284
  crypto_rand(b,n);
285
286
}

Roger Dingledine's avatar
Roger Dingledine committed
287
/** Initialize the DNS subsystem; called by the OR process. */
288
int
289
290
dns_init(void)
{
291
  init_cache_map();
292
  evdns_set_random_bytes_fn(dns_randfn_);
293
294
295
296
  if (server_mode(get_options())) {
    int r = configure_nameservers(1);
    return r;
  }
297
  return 0;
298
}
299

300
301
302
/** Called when DNS-related options change (or may have changed).  Returns -1
 * on failure, 0 on success. */
int
303
304
dns_reset(void)
{
305
  const or_options_t *options = get_options();
306
  if (! server_mode(options)) {
307
308
309
310
311
312
313
314

    if (!the_evdns_base) {
      if (!(the_evdns_base = evdns_base_new(tor_libevent_get_base(), 0))) {
        log_err(LD_BUG, "Couldn't create an evdns_base");
        return -1;
      }
    }

315
316
    evdns_base_clear_nameservers_and_suspend(the_evdns_base);
    evdns_base_search_clear(the_evdns_base);
317
318
319
320
    nameservers_configured = 0;
    tor_free(resolv_conf_fname);
    resolv_conf_mtime = 0;
  } else {
321
    if (configure_nameservers(0) < 0) {
322
      return -1;
323
    }
324
  }
325
  return 0;
326
327
}

Nick Mathewson's avatar
Nick Mathewson committed
328
329
/** Return true iff the most recent attempt to initialize the DNS subsystem
 * failed. */
330
331
332
333
334
335
int
has_dns_init_failed(void)
{
  return nameserver_config_failed;
}

336
337
/** Helper: Given a TTL from a DNS response, determine what TTL to give the
 * OP that asked us to resolve it. */
338
339
340
341
342
343
344
345
346
347
348
uint32_t
dns_clip_ttl(uint32_t ttl)
{
  if (ttl < MIN_DNS_TTL)
    return MIN_DNS_TTL;
  else if (ttl > MAX_DNS_TTL)
    return MAX_DNS_TTL;
  else
    return ttl;
}

349
350
/** Helper: Given a TTL from a DNS response, determine how long to hold it in
 * our cache. */
351
352
353
354
355
356
357
358
359
360
361
static uint32_t
dns_get_expiry_ttl(uint32_t ttl)
{
  if (ttl < MIN_DNS_TTL)
    return MIN_DNS_TTL;
  else if (ttl > MAX_DNS_ENTRY_AGE)
    return MAX_DNS_ENTRY_AGE;
  else
    return ttl;
}

362
/** Helper: free storage held by an entry in the DNS cache. */
363
static void
364
free_cached_resolve_(cached_resolve_t *r)
365
{
366
367
  if (!r)
    return;
Nick Mathewson's avatar
Nick Mathewson committed
368
  while (r->pending_connections) {
369
    pending_connection_t *victim = r->pending_connections;
370
371
372
    r->pending_connections = victim->next;
    tor_free(victim);
  }
373
374
  if (r->res_status_hostname == RES_STATUS_DONE_OK)
    tor_free(r->result_ptr.hostname);
375
  r->magic = 0xFF00FF00;
376
377
378
  tor_free(r);
}

379
380
381
/** Compare two cached_resolve_t pointers by expiry time, and return
 * less-than-zero, zero, or greater-than-zero as appropriate. Used for
 * the priority queue implementation. */
382
static int
383
compare_cached_resolves_by_expiry_(const void *_a, const void *_b)
384
{
385
  const cached_resolve_t *a = _a, *b = _b;
386
387
388
389
390
391
  if (a->expire < b->expire)
    return -1;
  else if (a->expire == b->expire)
    return 0;
  else
    return 1;
392
393
}

394
395
/** Priority queue of cached_resolve_t objects to let us know when they
 * will expire. */
396
397
static smartlist_t *cached_resolve_pqueue = NULL;

398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
static void
cached_resolve_add_answer(cached_resolve_t *resolve,
                          int query_type,
                          int dns_result,
                          const tor_addr_t *answer_addr,
                          const char *answer_hostname,
                          uint32_t ttl)
{
  if (query_type == DNS_PTR) {
    if (resolve->res_status_hostname != RES_STATUS_INFLIGHT)
      return;

    if (dns_result == DNS_ERR_NONE && answer_hostname) {
      resolve->result_ptr.hostname = tor_strdup(answer_hostname);
      resolve->res_status_hostname = RES_STATUS_DONE_OK;
    } else {
      resolve->result_ptr.err_hostname = dns_result;
      resolve->res_status_hostname = RES_STATUS_DONE_ERR;
    }
    resolve->ttl_hostname = ttl;
  } else if (query_type == DNS_IPv4_A) {
    if (resolve->res_status_ipv4 != RES_STATUS_INFLIGHT)
      return;

    if (dns_result == DNS_ERR_NONE && answer_addr) {
      tor_assert(tor_addr_family(answer_addr) == AF_INET);
      resolve->result_ipv4.addr_ipv4 = tor_addr_to_ipv4h(answer_addr);
      resolve->res_status_ipv4 = RES_STATUS_DONE_OK;
    } else {
      resolve->result_ipv4.err_ipv4 = dns_result;
      resolve->res_status_ipv4 = RES_STATUS_DONE_ERR;
    }

  } else if (query_type == DNS_IPv6_AAAA) {
    if (resolve->res_status_ipv6 != RES_STATUS_INFLIGHT)
      return;

    if (dns_result == DNS_ERR_NONE && answer_addr) {
      tor_assert(tor_addr_family(answer_addr) == AF_INET6);
      memcpy(&resolve->result_ipv6.addr_ipv6,
             tor_addr_to_in6(answer_addr),
             sizeof(struct in6_addr));
      resolve->res_status_ipv6 = RES_STATUS_DONE_OK;
    } else {
      resolve->result_ipv6.err_ipv6 = dns_result;
      resolve->res_status_ipv6 = RES_STATUS_DONE_ERR;
    }
  }
}

/*DOCDOC*/
static int
cached_resolve_have_all_answers(const cached_resolve_t *resolve)
{
  return (resolve->res_status_ipv4 != RES_STATUS_INFLIGHT &&
          resolve->res_status_ipv6 != RES_STATUS_INFLIGHT &&
          resolve->res_status_hostname != RES_STATUS_INFLIGHT);
}

457
458
/** Set an expiry time for a cached_resolve_t, and add it to the expiry
 * priority queue */
459
460
461
462
static void
set_expiry(cached_resolve_t *resolve, time_t expires)
{
  tor_assert(resolve && resolve->expire == 0);
463
  if (!cached_resolve_pqueue)
464
    cached_resolve_pqueue = smartlist_new();
465
466
  resolve->expire = expires;
  smartlist_pqueue_add(cached_resolve_pqueue,
467
                       compare_cached_resolves_by_expiry_,
468
                       STRUCT_OFFSET(cached_resolve_t, minheap_idx),
469
470
471
                       resolve);
}

472
/** Free all storage held in the DNS cache and related structures. */
473
474
475
void
dns_free_all(void)
{
476
  cached_resolve_t **ptr, **next, *item;
477
  assert_cache_ok();
478
479
480
  if (cached_resolve_pqueue) {
    SMARTLIST_FOREACH(cached_resolve_pqueue, cached_resolve_t *, res,
      {
481
        if (res->state == CACHE_STATE_DONE)
482
          free_cached_resolve_(res);
483
484
      });
  }
485
  for (ptr = HT_START(cache_map, &cache_root); ptr != NULL; ptr = next) {
486
    item = *ptr;
487
    next = HT_NEXT_RMV(cache_map, &cache_root, ptr);
488
    free_cached_resolve_(item);
489
  }
490
  HT_CLEAR(cache_map, &cache_root);
491
  smartlist_free(cached_resolve_pqueue);
492
  cached_resolve_pqueue = NULL;
493
  tor_free(resolv_conf_fname);
494
495
}

496
497
/** Remove every cached_resolve whose <b>expire</b> time is before or
 * equal to <b>now</b> from the cache. */
498
static void
499
purge_expired_resolves(time_t now)
500
{
Nick Mathewson's avatar
Nick Mathewson committed
501
  cached_resolve_t *resolve, *removed;
502
  pending_connection_t *pend;
503
  edge_connection_t *pendconn;
504

Nick Mathewson's avatar
Nick Mathewson committed
505
  assert_cache_ok();
506
507
508
509
510
511
512
513
  if (!cached_resolve_pqueue)
    return;

  while (smartlist_len(cached_resolve_pqueue)) {
    resolve = smartlist_get(cached_resolve_pqueue, 0);
    if (resolve->expire > now)
      break;
    smartlist_pqueue_pop(cached_resolve_pqueue,
514
                         compare_cached_resolves_by_expiry_,
515
                         STRUCT_OFFSET(cached_resolve_t, minheap_idx));
516

517
    if (resolve->state == CACHE_STATE_PENDING) {
518
      log_debug(LD_EXIT,
519
520
                "Expiring a dns resolve %s that's still pending. Forgot to "
                "cull it? DNS resolve didn't tell us about the timeout?",
521
                escaped_safe_str(resolve->address));
522
    } else if (resolve->state == CACHE_STATE_CACHED) {
523
524
525
526
527
528
529
530
      log_debug(LD_EXIT,
                "Forgetting old cached resolve (address %s, expires %lu)",
                escaped_safe_str(resolve->address),
                (unsigned long)resolve->expire);
      tor_assert(!resolve->pending_connections);
    } else {
      tor_assert(resolve->state == CACHE_STATE_DONE);
      tor_assert(!resolve->pending_connections);
531
    }
532

533
    if (resolve->pending_connections) {
534
      log_debug(LD_EXIT,
535
                "Closing pending connections on timed-out DNS resolve!");
536
537
538
539
      while (resolve->pending_connections) {
        pend = resolve->pending_connections;
        resolve->pending_connections = pend->next;
        /* Connections should only be pending if they have no socket. */
540
        tor_assert(!SOCKET_OK(pend->conn->base_.s));
541
        pendconn = pend->conn;
542
        if (!pendconn->base_.marked_for_close) {
543
544
545
546
          connection_edge_end(pendconn, END_STREAM_REASON_TIMEOUT);
          circuit_detach_stream(circuit_get_by_edge_conn(pendconn), pendconn);
          connection_free(TO_CONN(pendconn));
        }
547
548
        tor_free(pend);
      }
549
    }
550

551
    if (resolve->state == CACHE_STATE_CACHED ||
552
553
554
555
556
        resolve->state == CACHE_STATE_PENDING) {
      removed = HT_REMOVE(cache_map, &cache_root, resolve);
      if (removed != resolve) {
        log_err(LD_BUG, "The expired resolve we purged didn't match any in"
                " the cache. Tried to purge %s (%p); instead got %s (%p).",
557
                resolve->address, (void*)resolve,
558
                removed ? removed->address : "NULL", (void*)removed);
559
560
561
      }
      tor_assert(removed == resolve);
    } else {
562
      /* This should be in state DONE. Make sure it's not in the cache. */
563
564
      cached_resolve_t *tmp = HT_FIND(cache_map, &cache_root, resolve);
      tor_assert(tmp != resolve);
565
    }
566
567
    if (resolve->res_status_hostname == RES_STATUS_DONE_OK)
      tor_free(resolve->result_ptr.hostname);
568
569
    resolve->magic = 0xF0BBF0BB;
    tor_free(resolve);
570
  }
571

Nick Mathewson's avatar
Nick Mathewson committed
572
  assert_cache_ok();
573
574
}

575
576
577
578
/* argument for send_resolved_cell only, meaning "let the answer type be ipv4
 * or ipv6 depending on the connection's address". */
#define RESOLVED_TYPE_AUTO 0xff

579
580
/** Send a response to the RESOLVE request of a connection.
 * <b>answer_type</b> must be one of
581
 * RESOLVED_TYPE_(IPV4|IPV6|ERROR|ERROR_TRANSIENT|AUTO).
582
583
 *
 * If <b>circ</b> is provided, and we have a cached answer, send the
584
585
 * answer back along circ; otherwise, send the answer back along
 * <b>conn</b>'s attached circuit.
586
 */
587
static void
588
send_resolved_cell(edge_connection_t *conn, uint8_t answer_type)
589
590
{
  char buf[RELAY_PAYLOAD_SIZE];
591
  size_t buflen;
592
  uint32_t ttl;
593

594
595
596
597
598
599
600
601
602
603
  if (answer_type == RESOLVED_TYPE_AUTO) {
    sa_family_t family = tor_addr_family(&conn->base_.addr);
    if (family == AF_INET)
      answer_type = RESOLVED_TYPE_IPV4;
    else if (family == AF_INET6)
      answer_type = RESOLVED_TYPE_IPV6;
    else
      answer_type = RESOLVED_TYPE_ERROR_TRANSIENT;
  }

604
  buf[0] = answer_type;
605
  ttl = dns_clip_ttl(conn->address_ttl);
606
607
608
609
610

  switch (answer_type)
    {
    case RESOLVED_TYPE_IPV4:
      buf[1] = 4;
611
      set_uint32(buf+2, tor_addr_to_ipv4n(&conn->base_.addr));
612
      set_uint32(buf+6, htonl(ttl));
613
      buflen = 10;
614
      break;
615
616
617
618
619
620
621
622
623
    case RESOLVED_TYPE_IPV6:
      {
        const uint8_t *bytes = tor_addr_to_in6_addr8(&conn->base_.addr);
        buf[1] = 16;
        memcpy(buf+2, bytes, 16);
        set_uint32(buf+18, htonl(ttl));
        buflen = 22;
      }
      break;
624
625
    case RESOLVED_TYPE_ERROR_TRANSIENT:
    case RESOLVED_TYPE_ERROR:
626
627
      {
        const char *errmsg = "Error resolving hostname";
628
        size_t msglen = strlen(errmsg);
629

630
631
        buf[1] = msglen;
        strlcpy(buf+2, errmsg, sizeof(buf)-2);
632
        set_uint32(buf+2+msglen, htonl(ttl));
633
634
635
        buflen = 6+msglen;
        break;
      }
636
637
    default:
      tor_assert(0);
638
      return;
639
    }
640
  // log_notice(LD_EXIT, "Sending a regular RESOLVED reply: ");
Roger Dingledine's avatar
Roger Dingledine committed
641

642
  connection_edge_send_command(conn, RELAY_COMMAND_RESOLVED, buf, buflen);
643
644
}

645
646
647
/** Send a response to the RESOLVE request of a connection for an in-addr.arpa
 * address on connection <b>conn</b> which yielded the result <b>hostname</b>.
 * The answer type will be RESOLVED_HOSTNAME.
648
649
650
 *
 * If <b>circ</b> is provided, and we have a cached answer, send the
 * answer back along circ; otherwise, send the answer back along
651
 * <b>conn</b>'s attached circuit.
652
653
 */
static void
654
send_resolved_hostname_cell(edge_connection_t *conn, const char *hostname)
655
656
657
658
659
{
  char buf[RELAY_PAYLOAD_SIZE];
  size_t buflen;
  uint32_t ttl;
  size_t namelen = strlen(hostname);
660
  tor_assert(hostname);
661
662
663
664
665
666
667
668
669
670

  tor_assert(namelen < 256);
  ttl = dns_clip_ttl(conn->address_ttl);

  buf[0] = RESOLVED_TYPE_HOSTNAME;
  buf[1] = (uint8_t)namelen;
  memcpy(buf+2, hostname, namelen);
  set_uint32(buf+2+namelen, htonl(ttl));
  buflen = 2+namelen+4;

671
  // log_notice(LD_EXIT, "Sending a reply RESOLVED reply: %s", hostname);
672
  connection_edge_send_command(conn, RELAY_COMMAND_RESOLVED, buf, buflen);
673
  // log_notice(LD_EXIT, "Sent");
674
675
}

Roger Dingledine's avatar
Roger Dingledine committed
676
/** See if we have a cache entry for <b>exitconn</b>-\>address. If so,
Nick Mathewson's avatar
Nick Mathewson committed
677
 * if resolve valid, put it into <b>exitconn</b>-\>addr and return 1.
Roger Dingledine's avatar
Roger Dingledine committed
678
 * If resolve failed, free exitconn and return -1.
679
 *
680
681
682
683
684
 * (For EXIT_PURPOSE_RESOLVE connections, send back a RESOLVED error cell
 * on returning -1.  For EXIT_PURPOSE_CONNECT connections, there's no
 * need to send back an END cell, since connection_exit_begin_conn will
 * do that for us.)
 *
685
 * If we have a cached answer, send the answer back along <b>exitconn</b>'s
686
 * circuit.
687
 *
688
689
690
691
692
 * Else, if seen before and pending, add conn to the pending list,
 * and return 0.
 *
 * Else, if not seen before, add conn to pending list, hand to
 * dns farm, and return 0.
693
694
695
696
697
698
 *
 * Exitconn's on_circuit field must be set, but exitconn should not
 * yet be linked onto the n_streams/resolving_streams list of that circuit.
 * On success, link the connection to n_streams if it's an exit connection.
 * On "pending", link the connection to resolving streams.  Otherwise,
 * clear its on_circuit field.
699
 */
700
int
701
dns_resolve(edge_connection_t *exitconn)
702
703
704
{
  or_circuit_t *oncirc = TO_OR_CIRCUIT(exitconn->on_circuit);
  int is_resolve, r;
705
  int made_connection_pending = 0;
706
  char *hostname = NULL;
707
  is_resolve = exitconn->base_.purpose == EXIT_PURPOSE_RESOLVE;
708

709
710
  r = dns_resolve_impl(exitconn, is_resolve, oncirc, &hostname,
                       &made_connection_pending);
711

712
713
  switch (r) {
    case 1:
714
715
      /* We got an answer without a lookup -- either the answer was
       * cached, or it was obvious (like an IP address). */
716
      if (is_resolve) {
717
        /* Send the answer back right now, and detach. */
718
719
720
        if (hostname)
          send_resolved_hostname_cell(exitconn, hostname);
        else
721
          send_resolved_cell(exitconn, RESOLVED_TYPE_AUTO);
722
        exitconn->on_circuit = NULL;
723
      } else {
724
725
        /* Add to the n_streams list; the calling function will send back a
         * connected cell. */
726
727
728
729
730
        exitconn->next_stream = oncirc->n_streams;
        oncirc->n_streams = exitconn;
      }
      break;
    case 0:
731
732
      /* The request is pending: add the connection into the linked list of
       * resolving_streams on this circuit. */
733
      exitconn->base_.state = EXIT_CONN_STATE_RESOLVING;
734
735
736
737
738
      exitconn->next_stream = oncirc->resolving_streams;
      oncirc->resolving_streams = exitconn;
      break;
    case -2:
    case -1:
739
      /* The request failed before it could start: cancel this connection,
740
       * and stop everybody waiting for the same connection. */
741
742
743
744
      if (is_resolve) {
        send_resolved_cell(exitconn,
             (r == -1) ? RESOLVED_TYPE_ERROR : RESOLVED_TYPE_ERROR_TRANSIENT);
      }
745

746
      exitconn->on_circuit = NULL;
747

748
      dns_cancel_pending_resolve(exitconn->base_.address);
749

750
      if (!made_connection_pending && !exitconn->base_.marked_for_close) {
751
752
753
        /* If we made the connection pending, then we freed it already in
         * dns_cancel_pending_resolve().  If we marked it for close, it'll
         * get freed from the main loop.  Otherwise, can free it now. */
754
        connection_free(TO_CONN(exitconn));
755
      }
756
757
758
759
760
761
762
763
764
765
766
767
768
769
      break;
    default:
      tor_assert(0);
  }

  tor_free(hostname);
  return r;
}

/** Helper function for dns_resolve: same functionality, but does not handle:
 *     - marking connections on error and clearing their on_circuit
 *     - linking connections to n_streams/resolving_streams,
 *     - sending resolved cells if we have an answer/error right away,
 *
Roger Dingledine's avatar
Roger Dingledine committed
770
771
772
 * Return -2 on a transient error. If it's a reverse resolve and it's
 * successful, sets *<b>hostname_out</b> to a newly allocated string
 * holding the cached reverse DNS value.
773
774
775
776
 *
 * Set *<b>made_connection_pending_out</b> to true if we have placed
 * <b>exitconn</b> on the list of pending connections for some resolve; set it
 * to false otherwise.
777
778
779
 */
static int
dns_resolve_impl(edge_connection_t *exitconn, int is_resolve,
780
781
                 or_circuit_t *oncirc, char **hostname_out,
                 int *made_connection_pending_out)
782
{
783
784
785
  cached_resolve_t *resolve;
  cached_resolve_t search;
  pending_connection_t *pending_connection;
786
  int is_reverse = 0;
787
  const routerinfo_t *me;
788
  tor_addr_t addr;
789
  time_t now = time(NULL);
790
  int r;
791
  assert_connection_ok(TO_CONN(exitconn), 0);
792
  tor_assert(!SOCKET_OK(exitconn->base_.s));
793
  assert_cache_ok();
794
  tor_assert(oncirc);
795
  *made_connection_pending_out = 0;
796

797
  /* first check if exitconn->base_.address is an IP. If so, we already
798
   * know the answer. */
799
  if (tor_addr_parse(&addr, exitconn->base_.address) >= 0) {
800
801
    if (tor_addr_family(&addr) == AF_INET ||
        tor_addr_family(&addr) == AF_INET6) {
802
      tor_addr_copy(&exitconn->base_.addr, &addr);
803
804
805
      exitconn->address_ttl = DEFAULT_DNS_TTL;
      return 1;
    } else {
806
      /* XXXX unspec? Bogus? */
807
808
      return -1;
    }
809
  }
810

811
812
813
814
815
  /* If we're a non-exit, don't even do DNS lookups. */
  if (!(me = router_get_my_routerinfo()) ||
      policy_is_reject_star(me->exit_policy)) {
    return -1;
  }
816
  if (address_is_invalid_destination(exitconn->base_.address, 0)) {
817
818
    log(LOG_PROTOCOL_WARN, LD_EXIT,
        "Rejecting invalid destination address %s",
819
        escaped_safe_str(exitconn->base_.address));
820
821
    return -1;
  }
822
823

  /* then take this opportunity to see if there are any expired
824
   * resolves in the hash table. */
825
  purge_expired_resolves(now);
826

827
828
  /* lower-case exitconn->base_.address, so it's in canonical form */
  tor_strlower(exitconn->base_.address);
829

830
831
  /* Check whether this is a reverse lookup.  If it's malformed, or it's a
   * .in-addr.arpa address but this isn't a resolve request, kill the
832
   * connection.
833
   */
834
  if ((r = tor_addr_parse_PTR_name(&addr, exitconn->base_.address,
835
                                              AF_UNSPEC, 0)) != 0) {
836
    if (r == 1) {
837
      is_reverse = 1;
838
839
      if (tor_addr_is_internal(&addr, 0)) /* internal address? */
        return -1;
840
    }
841
842
843
844

    if (!is_reverse || !is_resolve) {
      if (!is_reverse)
        log_info(LD_EXIT, "Bad .in-addr.arpa address \"%s\"; sending error.",
845
                 escaped_safe_str(exitconn->base_.address));
846
847
848
849
      else if (!is_resolve)
        log_info(LD_EXIT,
                 "Attempt to connect to a .in-addr.arpa address \"%s\"; "
                 "sending error.",
850
                 escaped_safe_str(exitconn->base_.address));
851
852
853

      return -1;
    }
854
    //log_notice(LD_EXIT, "Looks like an address %s",
855
    //exitconn->base_.address);
856
  }
857
  exitconn->is_reverse_dns_lookup = is_reverse;
858

859
  /* now check the hash table to see if 'address' is already there. */
860
  strlcpy(search.address, exitconn->base_.address, sizeof(search.address));
861
  resolve = HT_FIND(cache_map, &cache_root, &search);
862
  if (resolve && resolve->expire > now) { /* already there */
863
    switch (resolve->state) {
864
865
      case CACHE_STATE_PENDING:
        /* add us to the pending list */
866
        pending_connection = tor_malloc_zero(
867
                                      sizeof(pending_connection_t));
868
        pending_connection->conn = exitconn;
Roger Dingledine's avatar
   
Roger Dingledine committed
869
870
        pending_connection->next = resolve->pending_connections;
        resolve->pending_connections = pending_connection;
871
        *made_connection_pending_out = 1;
872
        log_debug(LD_EXIT,"Connection (fd %d) waiting for pending DNS "
873
874
                  "resolve of %s", exitconn->base_.s,
                  escaped_safe_str(exitconn->base_.address));
Roger Dingledine's avatar
   
Roger Dingledine committed
875
        return 0;
876
877
      case CACHE_STATE_CACHED:
        log_debug(LD_EXIT,"Connection (fd %d) found cachedresult for %s",
878
                  exitconn->base_.s,
879
                  escaped_safe_str(resolve->address));
880
881
882

        return set_exitconn_info_from_resolve(exitconn, resolve, hostname_out);

883
884
885
      case CACHE_STATE_DONE:
        log_err(LD_BUG, "Found a 'DONE' dns resolve still in the cache.");
        tor_fragile_assert();
886
    }
Roger Dingledine's avatar
Roger Dingledine committed
887
    tor_assert(0);
Roger Dingledine's avatar
Roger Dingledine committed
888
  }
889
  tor_assert(!resolve);
Roger Dingledine's avatar
Roger Dingledine committed
890
  /* not there, need to add it */
891
  resolve = tor_malloc_zero(sizeof(cached_resolve_t));
892
  resolve->magic = CACHED_RESOLVE_MAGIC;
Roger Dingledine's avatar
Roger Dingledine committed
893
  resolve->state = CACHE_STATE_PENDING;
894
  resolve->minheap_idx = -1;
895
  strlcpy(resolve->address, exitconn->base_.address, sizeof(resolve->address));
Roger Dingledine's avatar
Roger Dingledine committed
896

897
  /* add this connection to the pending list */
898
  pending_connection = tor_malloc_zero(sizeof(pending_connection_t));
Roger Dingledine's avatar
Roger Dingledine committed
899
900
  pending_connection->conn = exitconn;
  resolve->pending_connections = pending_connection;
901
  *made_connection_pending_out = 1;
Roger Dingledine's avatar
Roger Dingledine committed
902

903
  /* Add this resolve to the cache and priority queue. */
904
  HT_INSERT(cache_map, &cache_root, resolve);
905
  set_expiry(resolve, now + RESOLVE_MAX_TIMEOUT);
906

907
  log_debug(LD_EXIT,"Launching %s.",
908
            escaped_safe_str(exitconn->base_.address));
909
  assert_cache_ok();
910

911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959