aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNick Mathewson <nickm@torproject.org>2014-08-15 17:37:39 -0400
committerNick Mathewson <nickm@torproject.org>2014-08-20 14:50:38 -0400
commit7f5a440421b122c2d594a89e21799078b3d7284a (patch)
tree57102a96d174dd5dca5ec7b2e3e7d79bf37d9c5d
parent82d4b60b91483ad2cf12a4feefc1c5020bf605b8 (diff)
downloadtor-7f5a440421b122c2d594a89e21799078b3d7284a.tar.gz
tor-7f5a440421b122c2d594a89e21799078b3d7284a.zip
Don't allocate an extra smartlist in the OOM handler
Fixes issue 10116
-rw-r--r--changes/bug101163
-rw-r--r--src/or/circuitlist.c19
2 files changed, 12 insertions, 10 deletions
diff --git a/changes/bug10116 b/changes/bug10116
new file mode 100644
index 0000000000..db7f7652ad
--- /dev/null
+++ b/changes/bug10116
@@ -0,0 +1,3 @@
+ o Minor features:
+ - When handling a low-memory situation, allocate less memory
+ for teporary data structures. Fixes issue 10115.
diff --git a/src/or/circuitlist.c b/src/or/circuitlist.c
index 60c40f51fa..d6bc67431f 100644
--- a/src/or/circuitlist.c
+++ b/src/or/circuitlist.c
@@ -1975,8 +1975,7 @@ circuits_compare_by_oldest_queued_item_(const void **a_, const void **b_)
void
circuits_handle_oom(size_t current_allocation)
{
- /* Let's hope there's enough slack space for this allocation here... */
- smartlist_t *circlist = smartlist_new();
+ smartlist_t *circlist;
size_t mem_to_recover;
size_t mem_recovered=0;
int n_circuits_killed=0;
@@ -2008,18 +2007,20 @@ circuits_handle_oom(size_t current_allocation)
tor_gettimeofday_cached_monotonic(&now);
now_ms = (uint32_t)tv_to_msec(&now);
- /* This algorithm itself assumes that you've got enough memory slack
- * to actually run it. */
- SMARTLIST_FOREACH_BEGIN(circuit_get_global_list(), circuit_t *, circ) {
+ circlist = circuit_get_global_list();
+ SMARTLIST_FOREACH_BEGIN(circlist, circuit_t *, circ) {
circ->age_tmp = circuit_max_queued_item_age(circ, now_ms);
- smartlist_add(circlist, circ);
- }
- SMARTLIST_FOREACH_END(circ);
+ } SMARTLIST_FOREACH_END(circ);
/* This is O(n log n); there are faster algorithms we could use instead.
* Let's hope this doesn't happen enough to be in the critical path. */
smartlist_sort(circlist, circuits_compare_by_oldest_queued_item_);
+ /* Fix up the indices before we run into trouble */
+ SMARTLIST_FOREACH_BEGIN(circlist, circuit_t *, circ) {
+ circ->global_circuitlist_idx = circ_sl_idx;
+ } SMARTLIST_FOREACH_END(circ);
+
/* Okay, now the worst circuits are at the front of the list. Let's mark
* them, and reclaim their storage aggressively. */
SMARTLIST_FOREACH_BEGIN(circlist, circuit_t *, circ) {
@@ -2051,8 +2052,6 @@ circuits_handle_oom(size_t current_allocation)
U64_PRINTF_ARG(mem_recovered),
n_circuits_killed,
smartlist_len(circlist) - n_circuits_killed);
-
- smartlist_free(circlist);
}
/** Verify that cpath layer <b>cp</b> has all of its invariants