diff options
author | Nick Mathewson <nickm@torproject.org> | 2014-03-23 00:20:05 -0400 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2014-03-23 00:20:05 -0400 |
commit | 2cfc4453c246bbd964cb9849bc5959bb1c510ae7 (patch) | |
tree | 67aa401eef9323e8baff9d01a45490bbd82e939c /src/or/circuitlist.c | |
parent | f4e2c72beef2821a6f30a31ad487d9d7911df0dc (diff) | |
parent | d769cab3e50979807a526b3ebc5c341c13b12e97 (diff) | |
download | tor-2cfc4453c246bbd964cb9849bc5959bb1c510ae7.tar.gz tor-2cfc4453c246bbd964cb9849bc5959bb1c510ae7.zip |
Merge remote-tracking branch 'public/bug9683_rebased'
Diffstat (limited to 'src/or/circuitlist.c')
-rw-r--r-- | src/or/circuitlist.c | 63 |
1 files changed, 59 insertions, 4 deletions
diff --git a/src/or/circuitlist.c b/src/or/circuitlist.c index b2eb730c8c..867a9cd0a3 100644 --- a/src/or/circuitlist.c +++ b/src/or/circuitlist.c @@ -1144,12 +1144,58 @@ void circuit_unlink_all_from_channel(channel_t *chan, int reason) { circuit_t *circ; + smartlist_t *detached = smartlist_new(); - channel_unlink_all_circuits(chan); +#define DEBUG_CIRCUIT_UNLINK_ALL - TOR_LIST_FOREACH(circ, &global_circuitlist, head) { + channel_unlink_all_circuits(chan, detached); + +#ifdef DEBUG_CIRCUIT_UNLINK_ALL + { + smartlist_t *detached_2 = smartlist_new(); + int mismatch = 0, badlen = 0; + + TOR_LIST_FOREACH(circ, &global_circuitlist, head) { + if (circ->n_chan == chan || + (!CIRCUIT_IS_ORIGIN(circ) && + TO_OR_CIRCUIT(circ)->p_chan == chan)) { + smartlist_add(detached_2, circ); + } + } + + if (smartlist_len(detached) != smartlist_len(detached_2)) { + log_warn(LD_BUG, "List of detached circuits had the wrong length! " + "(got %d, should have gotten %d)", + (int)smartlist_len(detached), + (int)smartlist_len(detached_2)); + badlen = 1; + } + smartlist_sort_pointers(detached); + smartlist_sort_pointers(detached_2); + + SMARTLIST_FOREACH(detached, circuit_t *, c, + if (c != smartlist_get(detached_2, c_sl_idx)) + mismatch = 1; + ); + + if (mismatch) + log_warn(LD_BUG, "Mismatch in list of detached circuits."); + + if (badlen || mismatch) { + smartlist_free(detached); + detached = detached_2; + } else { + log_notice(LD_CIRC, "List of %d circuits was as expected.", + (int)smartlist_len(detached)); + smartlist_free(detached_2); + } + } +#endif + + SMARTLIST_FOREACH_BEGIN(detached, circuit_t *, circ) { int mark = 0; if (circ->n_chan == chan) { + circuit_set_n_circid_chan(circ, 0, NULL); mark = 1; @@ -1165,9 +1211,16 @@ circuit_unlink_all_from_channel(channel_t *chan, int reason) mark = 1; } } - if (mark && !circ->marked_for_close) + if (!mark) { + log_warn(LD_BUG, "Circuit on detached list which I had no reason " + "to mark"); + continue; + } + if (!circ->marked_for_close) circuit_mark_for_close(circ, reason); - } + } SMARTLIST_FOREACH_END(circ); + + smartlist_free(detached); } /** Return a circ such that @@ -1541,6 +1594,7 @@ circuit_mark_for_close_, (circuit_t *circ, int reason, int line, channel_send_destroy(circ->n_circ_id, circ->n_chan, reason); } circuitmux_detach_circuit(circ->n_chan->cmux, circ); + circuit_set_n_circid_chan(circ, 0, NULL); } if (! CIRCUIT_IS_ORIGIN(circ)) { @@ -1574,6 +1628,7 @@ circuit_mark_for_close_, (circuit_t *circ, int reason, int line, channel_send_destroy(or_circ->p_circ_id, or_circ->p_chan, reason); } circuitmux_detach_circuit(or_circ->p_chan->cmux, circ); + circuit_set_p_circid_chan(or_circ, 0, NULL); } } else { origin_circuit_t *ocirc = TO_ORIGIN_CIRCUIT(circ); |