diff options
author | Nick Mathewson <nickm@torproject.org> | 2018-07-02 13:22:07 -0400 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2018-07-02 13:22:07 -0400 |
commit | bfcfeaed0772cd9238c3fa4d1c4a6db4f23ad2a3 (patch) | |
tree | d322687e01ae0e8cec9edde3bdf4c7688dc3f4c6 | |
parent | cf8c3abff179b4550404bb9978a9d2b5ad18fc34 (diff) | |
parent | 46b06cd6999439608f4a8a34bb68f6fe6a6311e9 (diff) | |
download | tor-bfcfeaed0772cd9238c3fa4d1c4a6db4f23ad2a3.tar.gz tor-bfcfeaed0772cd9238c3fa4d1c4a6db4f23ad2a3.zip |
Merge branch 'mikeperry_bug26214-rebased_squashed' into maint-0.3.4
-rw-r--r-- | changes/bug26214 | 3 | ||||
-rw-r--r-- | src/or/or.h | 1 | ||||
-rw-r--r-- | src/or/relay.c | 24 | ||||
-rw-r--r-- | src/test/test_relaycell.c | 17 |
4 files changed, 42 insertions, 3 deletions
diff --git a/changes/bug26214 b/changes/bug26214 new file mode 100644 index 0000000000..4277b9c6ec --- /dev/null +++ b/changes/bug26214 @@ -0,0 +1,3 @@ + o Minor bugfixes (correctness, flow control): + - Upon receiving a stream-level SENDME cell, verify that our window has + not grown too large. Fixes bug 26214; bugfix on svn r54 (pre-0.0.1) diff --git a/src/or/or.h b/src/or/or.h index e106ec66fa..db8f9544fe 100644 --- a/src/or/or.h +++ b/src/or/or.h @@ -929,6 +929,7 @@ typedef enum { /** Initial value on both sides of a stream transmission window when the * stream is initialized. Measured in cells. */ #define STREAMWINDOW_START 500 +#define STREAMWINDOW_START_MAX 500 /** Amount to increment a stream window when we get a stream SENDME. */ #define STREAMWINDOW_INCREMENT 50 diff --git a/src/or/relay.c b/src/or/relay.c index 50f59d6b99..3632678af6 100644 --- a/src/or/relay.c +++ b/src/or/relay.c @@ -1752,8 +1752,7 @@ connection_edge_process_relay_cell(cell_t *cell, circuit_t *circ, circuit_resume_edge_reading(circ, layer_hint); /* We count circuit-level sendme's as valid delivered data because - * they are rate limited. Note that we cannot count stream - * sendme's because the other end could send as many as they like. + * they are rate limited. */ if (CIRCUIT_IS_ORIGIN(circ)) { circuit_read_valid_data(TO_ORIGIN_CIRCUIT(circ), @@ -1783,6 +1782,27 @@ connection_edge_process_relay_cell(cell_t *cell, circuit_t *circ, rh.stream_id); return 0; } + + /* Don't allow the other endpoint to request more than our maximim + * (ie initial) stream SENDME window worth of data. Well-behaved + * stock clients will not request more than this max (as per the check + * in the while loop of connection_edge_consider_sending_sendme()). + */ + if (conn->package_window + STREAMWINDOW_INCREMENT > + STREAMWINDOW_START_MAX) { + static struct ratelim_t stream_warn_ratelim = RATELIM_INIT(600); + log_fn_ratelim(&stream_warn_ratelim,LOG_PROTOCOL_WARN, LD_PROTOCOL, + "Unexpected stream sendme cell. Closing circ (window %d).", + conn->package_window); + return -END_CIRC_REASON_TORPROTOCOL; + } + + /* At this point, the stream sendme is valid */ + if (CIRCUIT_IS_ORIGIN(circ)) { + circuit_read_valid_data(TO_ORIGIN_CIRCUIT(circ), + rh.length); + } + conn->package_window += STREAMWINDOW_INCREMENT; log_debug(domain,"stream-level sendme, packagewindow now %d.", conn->package_window); diff --git a/src/test/test_relaycell.c b/src/test/test_relaycell.c index 841174982c..1bd17b73bf 100644 --- a/src/test/test_relaycell.c +++ b/src/test/test_relaycell.c @@ -240,11 +240,26 @@ test_circbw_relay(void *arg) circ->cpath); ASSERT_UNCOUNTED_BW(); - /* Sendme on stream: not counted */ + /* Sendme on valid stream: counted */ ENTRY_TO_CONN(entryconn)->outbuf_flushlen = 0; PACK_CELL(1, RELAY_COMMAND_SENDME, "Data1234"); connection_edge_process_relay_cell(&cell, TO_CIRCUIT(circ), edgeconn, circ->cpath); + ASSERT_COUNTED_BW(); + + /* Sendme on valid stream with full window: not counted */ + ENTRY_TO_CONN(entryconn)->outbuf_flushlen = 0; + PACK_CELL(1, RELAY_COMMAND_SENDME, "Data1234"); + edgeconn->package_window = 500; + connection_edge_process_relay_cell(&cell, TO_CIRCUIT(circ), edgeconn, + circ->cpath); + ASSERT_UNCOUNTED_BW(); + + /* Sendme on unknown stream: not counted */ + ENTRY_TO_CONN(entryconn)->outbuf_flushlen = 0; + PACK_CELL(1, RELAY_COMMAND_SENDME, "Data1234"); + connection_edge_process_relay_cell(&cell, TO_CIRCUIT(circ), NULL, + circ->cpath); ASSERT_UNCOUNTED_BW(); /* Sendme on circuit with full window: not counted */ |