mirror of
https://gitlab.torproject.org/tpo/core/tor.git
synced 2024-11-28 14:23:30 +01:00
Ticket #25573: Check half-opened stream ids when choosing a new one
Avoid data corrupton by avoiding mixing up old stream ids with new ones. This commit changes client behavior.
This commit is contained in:
parent
c56f63eadb
commit
144647031a
@ -2813,6 +2813,11 @@ get_unique_stream_id_by_circ(origin_circuit_t *circ)
|
|||||||
for (tmpconn = circ->p_streams; tmpconn; tmpconn=tmpconn->next_stream)
|
for (tmpconn = circ->p_streams; tmpconn; tmpconn=tmpconn->next_stream)
|
||||||
if (tmpconn->stream_id == test_stream_id)
|
if (tmpconn->stream_id == test_stream_id)
|
||||||
goto again;
|
goto again;
|
||||||
|
|
||||||
|
if (connection_half_edge_find_stream_id(circ->half_streams,
|
||||||
|
test_stream_id))
|
||||||
|
goto again;
|
||||||
|
|
||||||
return test_stream_id;
|
return test_stream_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -617,6 +617,65 @@ test_halfstream_insertremove(void *arg)
|
|||||||
subtest_halfstream_insertremove(1000);
|
subtest_halfstream_insertremove(1000);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
test_halfstream_wrap(void *arg)
|
||||||
|
{
|
||||||
|
origin_circuit_t *circ =
|
||||||
|
helper_create_origin_circuit(CIRCUIT_PURPOSE_C_GENERAL, 0);
|
||||||
|
edge_connection_t *edgeconn;
|
||||||
|
entry_connection_t *entryconn;
|
||||||
|
|
||||||
|
circ->cpath->state = CPATH_STATE_AWAITING_KEYS;
|
||||||
|
circ->cpath->deliver_window = CIRCWINDOW_START;
|
||||||
|
|
||||||
|
entryconn = fake_entry_conn(circ, 23);
|
||||||
|
edgeconn = ENTRY_TO_EDGE_CONN(entryconn);
|
||||||
|
|
||||||
|
(void)arg;
|
||||||
|
|
||||||
|
/* Suppress the WARN message we generate in this test */
|
||||||
|
setup_full_capture_of_logs(LOG_WARN);
|
||||||
|
MOCK(connection_mark_for_close_internal_, mock_mark_for_close);
|
||||||
|
|
||||||
|
/* Verify that get_unique_stream_id_by_circ() can wrap uint16_t */
|
||||||
|
circ->next_stream_id = 65530;
|
||||||
|
halfstream_insert(circ, edgeconn, NULL, 7, 0);
|
||||||
|
tt_int_op(circ->next_stream_id, OP_EQ, 2);
|
||||||
|
tt_int_op(smartlist_len(circ->half_streams), OP_EQ, 7);
|
||||||
|
|
||||||
|
/* Insert full-1 */
|
||||||
|
halfstream_insert(circ, edgeconn, NULL,
|
||||||
|
65534-smartlist_len(circ->half_streams), 0);
|
||||||
|
tt_int_op(smartlist_len(circ->half_streams), OP_EQ, 65534);
|
||||||
|
|
||||||
|
/* Verify that we can get_unique_stream_id_by_circ() successfully */
|
||||||
|
edgeconn->stream_id = get_unique_stream_id_by_circ(circ);
|
||||||
|
tt_int_op(edgeconn->stream_id, OP_NE, 0); /* 0 is failure */
|
||||||
|
|
||||||
|
/* Insert an opened stream on the circ with that id */
|
||||||
|
ENTRY_TO_CONN(entryconn)->marked_for_close = 0;
|
||||||
|
ENTRY_TO_CONN(entryconn)->outbuf_flushlen = 0;
|
||||||
|
edgeconn->base_.state = AP_CONN_STATE_CONNECT_WAIT;
|
||||||
|
circ->p_streams = edgeconn;
|
||||||
|
|
||||||
|
/* Verify that get_unique_stream_id_by_circ() fails */
|
||||||
|
tt_int_op(get_unique_stream_id_by_circ(circ), OP_EQ, 0); /* 0 is failure */
|
||||||
|
|
||||||
|
/* eof the one opened stream. Verify it is now in half-closed */
|
||||||
|
tt_int_op(smartlist_len(circ->half_streams), OP_EQ, 65534);
|
||||||
|
connection_edge_reached_eof(edgeconn);
|
||||||
|
tt_int_op(smartlist_len(circ->half_streams), OP_EQ, 65535);
|
||||||
|
|
||||||
|
/* Verify get_unique_stream_id_by_circ() fails due to full half-closed */
|
||||||
|
circ->p_streams = NULL;
|
||||||
|
tt_int_op(get_unique_stream_id_by_circ(circ), OP_EQ, 0); /* 0 is failure */
|
||||||
|
|
||||||
|
done:
|
||||||
|
circuit_free_(TO_CIRCUIT(circ));
|
||||||
|
connection_free_minimal(ENTRY_TO_CONN(entryconn));
|
||||||
|
UNMOCK(connection_mark_for_close_internal_);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
test_circbw_relay(void *arg)
|
test_circbw_relay(void *arg)
|
||||||
{
|
{
|
||||||
@ -992,6 +1051,7 @@ struct testcase_t relaycell_tests[] = {
|
|||||||
{ "resolved", test_relaycell_resolved, TT_FORK, NULL, NULL },
|
{ "resolved", test_relaycell_resolved, TT_FORK, NULL, NULL },
|
||||||
{ "circbw", test_circbw_relay, TT_FORK, NULL, NULL },
|
{ "circbw", test_circbw_relay, TT_FORK, NULL, NULL },
|
||||||
{ "halfstream", test_halfstream_insertremove, TT_FORK, NULL, NULL },
|
{ "halfstream", test_halfstream_insertremove, TT_FORK, NULL, NULL },
|
||||||
|
{ "streamwrap", test_halfstream_wrap, TT_FORK, NULL, NULL },
|
||||||
END_OF_TESTCASES
|
END_OF_TESTCASES
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user