123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178 |
- /* Copyright (c) 2014, The Tor Project, Inc. */
- /* See LICENSE for licensing information */
- #define ROUTERLIST_PRIVATE
- #include "or.h"
- #include "routerlist.h"
- #include "directory.h"
- #include "connection.h"
- #include "test.h"
- /* 4 digests + 3 sep + pre + post + NULL */
- static char output[4*BASE64_DIGEST256_LEN+3+2+2+1];
- static void
- mock_get_from_dirserver(uint8_t dir_purpose, uint8_t router_purpose,
- const char *resource, int pds_flags,
- download_want_authority_t want_authority)
- {
- (void)dir_purpose;
- (void)router_purpose;
- (void)pds_flags;
- (void)want_authority;
- tt_assert(resource);
- strlcpy(output, resource, sizeof(output));
- done:
- ;
- }
- static void
- test_routerlist_initiate_descriptor_downloads(void *arg)
- {
- const char *prose = "unhurried and wise, we perceive.";
- smartlist_t *digests = smartlist_new();
- (void)arg;
- for (int i = 0; i < 20; i++) {
- smartlist_add(digests, (char*)prose);
- }
- MOCK(directory_get_from_dirserver, mock_get_from_dirserver);
- initiate_descriptor_downloads(NULL, DIR_PURPOSE_FETCH_MICRODESC,
- digests, 3, 7, 0);
- UNMOCK(directory_get_from_dirserver);
- tt_str_op(output, OP_EQ, "d/"
- "dW5odXJyaWVkIGFuZCB3aXNlLCB3ZSBwZXJjZWl2ZS4-"
- "dW5odXJyaWVkIGFuZCB3aXNlLCB3ZSBwZXJjZWl2ZS4-"
- "dW5odXJyaWVkIGFuZCB3aXNlLCB3ZSBwZXJjZWl2ZS4-"
- "dW5odXJyaWVkIGFuZCB3aXNlLCB3ZSBwZXJjZWl2ZS4"
- ".z");
- done:
- smartlist_free(digests);
- }
- static int count = 0;
- static void
- mock_initiate_descriptor_downloads(const routerstatus_t *source,
- int purpose, smartlist_t *digests,
- int lo, int hi, int pds_flags)
- {
- (void)source;
- (void)purpose;
- (void)digests;
- (void)pds_flags;
- (void)hi;
- (void)lo;
- count += 1;
- }
- static void
- test_routerlist_launch_descriptor_downloads(void *arg)
- {
- smartlist_t *downloadable = smartlist_new();
- time_t now = time(NULL);
- char *cp;
- (void)arg;
- for (int i = 0; i < 100; i++) {
- cp = tor_malloc(DIGEST256_LEN);
- tt_assert(cp);
- crypto_rand(cp, DIGEST256_LEN);
- smartlist_add(downloadable, cp);
- }
- MOCK(initiate_descriptor_downloads, mock_initiate_descriptor_downloads);
- launch_descriptor_downloads(DIR_PURPOSE_FETCH_MICRODESC, downloadable,
- NULL, now);
- tt_int_op(3, ==, count);
- UNMOCK(initiate_descriptor_downloads);
- done:
- SMARTLIST_FOREACH(downloadable, char *, cp1, tor_free(cp1));
- smartlist_free(downloadable);
- }
- connection_t *mocked_connection = NULL;
- /* Mock connection_get_by_type_addr_port_purpose by returning
- * mocked_connection. */
- static connection_t *
- mock_connection_get_by_type_addr_port_purpose(int type,
- const tor_addr_t *addr,
- uint16_t port, int purpose)
- {
- (void)type;
- (void)addr;
- (void)port;
- (void)purpose;
- return mocked_connection;
- }
- #define TEST_ADDR_STR "127.0.0.1"
- #define TEST_DIR_PORT 12345
- static void
- test_routerlist_router_is_already_dir_fetching(void *arg)
- {
- (void)arg;
- tor_addr_port_t test_ap, null_addr_ap, zero_port_ap;
- /* Setup */
- tor_addr_parse(&test_ap.addr, TEST_ADDR_STR);
- test_ap.port = TEST_DIR_PORT;
- tor_addr_make_null(&null_addr_ap.addr, AF_INET6);
- null_addr_ap.port = TEST_DIR_PORT;
- tor_addr_parse(&zero_port_ap.addr, TEST_ADDR_STR);
- zero_port_ap.port = 0;
- MOCK(connection_get_by_type_addr_port_purpose,
- mock_connection_get_by_type_addr_port_purpose);
- /* Test that we never get 1 from a NULL connection */
- mocked_connection = NULL;
- tt_assert(router_is_already_dir_fetching(&test_ap, 1, 1) == 0);
- tt_assert(router_is_already_dir_fetching(&test_ap, 1, 0) == 0);
- tt_assert(router_is_already_dir_fetching(&test_ap, 0, 1) == 0);
- /* We always expect 0 in these cases */
- tt_assert(router_is_already_dir_fetching(&test_ap, 0, 0) == 0);
- tt_assert(router_is_already_dir_fetching(NULL, 1, 1) == 0);
- tt_assert(router_is_already_dir_fetching(&null_addr_ap, 1, 1) == 0);
- tt_assert(router_is_already_dir_fetching(&zero_port_ap, 1, 1) == 0);
- /* Test that we get 1 with a connection in the appropriate circumstances */
- mocked_connection = connection_new(CONN_TYPE_DIR, AF_INET);
- tt_assert(router_is_already_dir_fetching(&test_ap, 1, 1) == 1);
- tt_assert(router_is_already_dir_fetching(&test_ap, 1, 0) == 1);
- tt_assert(router_is_already_dir_fetching(&test_ap, 0, 1) == 1);
- /* Test that we get 0 even with a connection in the appropriate
- * circumstances */
- tt_assert(router_is_already_dir_fetching(&test_ap, 0, 0) == 0);
- tt_assert(router_is_already_dir_fetching(NULL, 1, 1) == 0);
- tt_assert(router_is_already_dir_fetching(&null_addr_ap, 1, 1) == 0);
- tt_assert(router_is_already_dir_fetching(&zero_port_ap, 1, 1) == 0);
- done:
- /* If a connection is never set up, connection_free chokes on it. */
- buf_free(mocked_connection->inbuf);
- buf_free(mocked_connection->outbuf);
- tor_free(mocked_connection);
- UNMOCK(connection_get_by_type_addr_port_purpose);
- }
- #undef TEST_ADDR_STR
- #undef TEST_DIR_PORT
- #define NODE(name, flags) \
- { #name, test_routerlist_##name, (flags), NULL, NULL }
- struct testcase_t routerlist_tests[] = {
- NODE(initiate_descriptor_downloads, 0),
- NODE(launch_descriptor_downloads, 0),
- NODE(router_is_already_dir_fetching, TT_FORK),
- END_OF_TESTCASES
- };
|