[or-cvs] r10548: more building blocks towards being able to fetch bridge desc (tor/trunk/src/or)
arma at seul.org
arma at seul.org
Sun Jun 10 07:34:21 UTC 2007
Author: arma
Date: 2007-06-10 03:34:21 -0400 (Sun, 10 Jun 2007)
New Revision: 10548
Modified:
tor/trunk/src/or/circuitbuild.c
tor/trunk/src/or/config.c
tor/trunk/src/or/directory.c
tor/trunk/src/or/or.h
tor/trunk/src/or/router.c
tor/trunk/src/or/routerlist.c
Log:
more building blocks towards being able to fetch bridge descriptors
Modified: tor/trunk/src/or/circuitbuild.c
===================================================================
--- tor/trunk/src/or/circuitbuild.c 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/circuitbuild.c 2007-06-10 07:34:21 UTC (rev 10548)
@@ -2622,3 +2622,79 @@
return 0;
}
+typedef struct {
+ uint32_t addr;
+ uint16_t port;
+ char identity[DIGEST_LEN];
+} bridge_info_t;
+
+/** A list of known bridges. */
+static smartlist_t *bridge_list = NULL;
+
+/** Initialize the bridge list to empty, creating it if needed. */
+void
+clear_bridge_list(void)
+{
+ if (!bridge_list)
+ bridge_list = smartlist_create();
+ SMARTLIST_FOREACH(bridge_list, bridge_info_t *, b, tor_free(b));
+ smartlist_clear(bridge_list);
+}
+
+/** Remember a new bridge at <b>addr</b>:<b>port</b>. If <b>digest</b>
+ * is set, it tells us the identity key too. */
+void
+bridge_add_from_config(uint32_t addr, uint16_t port, char *digest)
+{
+ bridge_info_t *b = tor_malloc_zero(sizeof(bridge_info_t));
+ b->addr = addr;
+ b->port = port;
+ if (digest)
+ memcpy(b->identity, digest, DIGEST_LEN);
+ if (!bridge_list)
+ bridge_list = smartlist_create();
+ smartlist_add(bridge_list, b);
+}
+
+/** For each bridge in our list for which we don't currently have a
+ * descriptor, fetch a new copy of its descriptor -- either directly
+ * from the bridge or via a bridge authority. */
+void
+learn_bridge_descriptors(void)
+{
+ char address_buf[INET_NTOA_BUF_LEN+1];
+ struct in_addr in;
+ or_options_t *options = get_options();
+ int num_bridge_auths = get_n_authorities(BRIDGE_AUTHORITY);
+
+ if (!bridge_list)
+ return;
+
+ SMARTLIST_FOREACH(bridge_list, bridge_info_t *, bridge,
+ {
+ if (router_get_by_digest(bridge->identity))
+ continue; /* we've already got one. great. */
+ in.s_addr = htonl(bridge->addr);
+ tor_inet_ntoa(&in, address_buf, sizeof(address_buf));
+
+ if (tor_digest_is_zero(bridge->identity) ||
+ !options->UpdateBridgesFromAuthority ||
+ !num_bridge_auths) {
+ if (!connection_get_by_type_addr_port_purpose(
+ CONN_TYPE_DIR, bridge->addr, bridge->port,
+ DIR_PURPOSE_FETCH_SERVERDESC)) {
+ /* we need to ask the bridge itself for its descriptor. */
+ directory_initiate_command(address_buf, bridge->addr,
+ bridge->port, 0,
+ 1, bridge->identity,
+ DIR_PURPOSE_FETCH_SERVERDESC,
+ ROUTER_PURPOSE_BRIDGE,
+ 0, "authority", NULL, 0);
+ }
+ } else {
+ /* we have a digest and we want to ask an authority. */
+ // XXX
+ }
+ });
+}
+
Modified: tor/trunk/src/or/config.c
===================================================================
--- tor/trunk/src/or/config.c 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/config.c 2007-06-10 07:34:21 UTC (rev 10548)
@@ -263,6 +263,7 @@
VAR("TransListenAddress", LINELIST, TransListenAddress, NULL),
VAR("TransPort", UINT, TransPort, "0"),
VAR("TunnelDirConns", BOOL, TunnelDirConns, "0"),
+ VAR("UpdateBridgesFromAuthority",BOOL,UpdateBridgesFromAuthority,"0"),
VAR("UseBridges", BOOL, UseBridges, "0"),
VAR("UseEntryGuards", BOOL, UseEntryGuards, "1"),
VAR("User", STRING, User, NULL),
@@ -952,6 +953,7 @@
add_default_trusted_dirservers();
}
+ clear_bridge_list();
if (options->Bridges) {
for (cl = options->Bridges; cl; cl = cl->next) {
if (parse_bridge_line(cl->value, 0)<0) {
@@ -3606,7 +3608,7 @@
log_debug(LD_DIR, "Bridge at %s:%d (%s)", address,
(int)port,
fingerprint ? fingerprint : "no key listed");
-// bridge_add_from_config(addr, port, fingerprint ? digest : NULL);
+ bridge_add_from_config(addr, port, fingerprint ? digest : NULL);
}
r = 0;
Modified: tor/trunk/src/or/directory.c
===================================================================
--- tor/trunk/src/or/directory.c 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/directory.c 2007-06-10 07:34:21 UTC (rev 10548)
@@ -177,7 +177,9 @@
}
post_via_tor = purpose_needs_anonymity(purpose) ||
!fascist_firewall_allows_address_dir(ds->addr, ds->dir_port);
- directory_initiate_command_routerstatus(rs, purpose, post_via_tor,
+ directory_initiate_command_routerstatus(rs, purpose,
+ ROUTER_PURPOSE_GENERAL,
+ post_via_tor,
NULL, payload, upload_len);
});
if (!found) {
@@ -194,18 +196,18 @@
* down, mark them up and try again.
*/
void
-directory_get_from_dirserver(uint8_t purpose, const char *resource,
+directory_get_from_dirserver(uint8_t dir_purpose, const char *resource,
int retry_if_no_servers)
{
routerstatus_t *rs = NULL;
or_options_t *options = get_options();
int prefer_authority = server_mode(options) && options->DirPort != 0;
- int directconn = !purpose_needs_anonymity(purpose);
+ int directconn = !purpose_needs_anonymity(dir_purpose);
authority_type_t type;
/* FFFF we could break this switch into its own function, and call
* it elsewhere in directory.c. -RD */
- switch (purpose) {
+ switch (dir_purpose) {
case DIR_PURPOSE_FETCH_EXTRAINFO:
type = EXTRAINFO_CACHE | V2_AUTHORITY;
break;
@@ -221,7 +223,7 @@
type = HIDSERV_AUTHORITY;
break;
default:
- log_warn(LD_BUG, "Unexpected purpose %d", (int)purpose);
+ log_warn(LD_BUG, "Unexpected purpose %d", (int)dir_purpose);
return;
}
@@ -240,13 +242,13 @@
retry_if_no_servers);
if (!rs) {
const char *which;
- if (purpose == DIR_PURPOSE_FETCH_DIR)
+ if (dir_purpose == DIR_PURPOSE_FETCH_DIR)
which = "directory";
- else if (purpose == DIR_PURPOSE_FETCH_RUNNING_LIST)
+ else if (dir_purpose == DIR_PURPOSE_FETCH_RUNNING_LIST)
which = "status list";
- else if (purpose == DIR_PURPOSE_FETCH_NETWORKSTATUS)
+ else if (dir_purpose == DIR_PURPOSE_FETCH_NETWORKSTATUS)
which = "network status";
- else // if (purpose == DIR_PURPOSE_FETCH_NETWORKSTATUS)
+ else // if (dir_purpose == DIR_PURPOSE_FETCH_NETWORKSTATUS)
which = "server descriptors";
log_info(LD_DIR,
"No router found for %s; falling back to dirserver list",
@@ -260,7 +262,7 @@
}
if (!directconn) {
/* Never use fascistfirewall; we're going via Tor. */
- if (purpose == DIR_PURPOSE_FETCH_RENDDESC) {
+ if (dir_purpose == DIR_PURPOSE_FETCH_RENDDESC) {
/* only ask hidserv authorities, any of them will do */
rs = router_pick_trusteddirserver(HIDSERV_AUTHORITY, 0, 0,
retry_if_no_servers);
@@ -275,24 +277,29 @@
}
if (rs)
- directory_initiate_command_routerstatus(rs, purpose, !directconn,
+ directory_initiate_command_routerstatus(rs, dir_purpose,
+ ROUTER_PURPOSE_GENERAL,
+ !directconn,
resource, NULL, 0);
else {
log_notice(LD_DIR,
"While fetching directory info, "
"no running dirservers known. Will try again later. "
- "(purpose %d)", purpose);
- if (!purpose_needs_anonymity(purpose)) {
+ "(purpose %d)", dir_purpose);
+ if (!purpose_needs_anonymity(dir_purpose)) {
/* remember we tried them all and failed. */
directory_all_unreachable(time(NULL));
}
}
}
-/** Launch a new connection to the directory server <b>status</b> to upload or
- * download a server or rendezvous descriptor. <b>purpose</b> determines what
+/** Launch a new connection to the directory server <b>status</b> to
+ * upload or download a server or rendezvous
+ * descriptor. <b>dir_purpose</b> determines what
* kind of directory connection we're launching, and must be one of
- * DIR_PURPOSE_{FETCH|UPLOAD}_{DIR|RENDDESC}.
+ * DIR_PURPOSE_{FETCH|UPLOAD}_{DIR|RENDDESC}. <b>router_purpose</b>
+ * specifies the descriptor purposes we have in mind (currently only
+ * used for FETCH_DIR).
*
* When uploading, <b>payload</b> and <b>payload_len</b> determine the content
* of the HTTP post. Otherwise, <b>payload</b> should be NULL.
@@ -302,7 +309,8 @@
*/
void
directory_initiate_command_routerstatus(routerstatus_t *status,
- uint8_t purpose,
+ uint8_t dir_purpose,
+ uint8_t router_purpose,
int anonymized_connection,
const char *resource,
const char *payload,
@@ -323,7 +331,8 @@
status->or_port, status->dir_port,
status->version_supports_begindir,
status->identity_digest,
- purpose, anonymized_connection, resource,
+ dir_purpose, router_purpose,
+ anonymized_connection, resource,
payload, payload_len);
}
@@ -441,8 +450,8 @@
void
directory_initiate_command(const char *address, uint32_t addr,
uint16_t or_port, uint16_t dir_port,
- int supports_begindir,
- const char *digest, uint8_t purpose,
+ int supports_begindir, const char *digest,
+ uint8_t dir_purpose, uint8_t router_purpose,
int anonymized_connection, const char *resource,
const char *payload, size_t payload_len)
{
@@ -460,7 +469,7 @@
log_debug(LD_DIR, "anonymized %d, want_to_tunnel %d.",
anonymized_connection, want_to_tunnel);
- switch (purpose) {
+ switch (dir_purpose) {
case DIR_PURPOSE_FETCH_DIR:
log_debug(LD_DIR,"initiating directory fetch");
break;
@@ -498,7 +507,8 @@
conn->_base.address = tor_strdup(address);
memcpy(conn->identity_digest, digest, DIGEST_LEN);
- conn->_base.purpose = purpose;
+ conn->_base.purpose = dir_purpose;
+ conn->router_purpose = router_purpose;
/* give it an initial state */
conn->_base.state = DIR_CONN_STATE_CONNECTING;
@@ -524,7 +534,7 @@
/* fall through */
case 0:
/* queue the command on the outbuf */
- directory_send_command(conn, purpose, 1, resource,
+ directory_send_command(conn, dir_purpose, 1, resource,
payload, payload_len);
connection_watch_events(TO_CONN(conn), EV_READ | EV_WRITE);
/* writable indicates finish, readable indicates broken link,
@@ -557,7 +567,7 @@
}
conn->_base.state = DIR_CONN_STATE_CLIENT_SENDING;
/* queue the command on the outbuf */
- directory_send_command(conn, purpose, 0, resource,
+ directory_send_command(conn, dir_purpose, 0, resource,
payload, payload_len);
connection_watch_events(TO_CONN(conn), EV_READ | EV_WRITE);
connection_start_reading(TO_CONN(linked_conn));
@@ -1256,7 +1266,8 @@
if (was_ei) {
router_load_extrainfo_from_string(body, NULL, SAVED_NOWHERE, which);
} else {
- router_load_routers_from_string(body, NULL, SAVED_NOWHERE, which);
+ router_load_routers_from_string(body, NULL, SAVED_NOWHERE, which,
+ conn->router_purpose);
directory_info_has_arrived(now, 0);
}
}
Modified: tor/trunk/src/or/or.h
===================================================================
--- tor/trunk/src/or/or.h 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/or.h 2007-06-10 07:34:21 UTC (rev 10548)
@@ -934,6 +934,9 @@
DIR_SPOOL_EXTRA_BY_DIGEST, DIR_SPOOL_EXTRA_BY_FP,
DIR_SPOOL_CACHED_DIR, DIR_SPOOL_NETWORKSTATUS
} dir_spool_src : 3;
+ /** If we're fetching descriptors, what router purpose shall we assign
+ * to them? */
+ uint8_t router_purpose;
/** List of fingerprints for networkstatuses or desriptors to be spooled. */
smartlist_t *fingerprint_stack;
/** A cached_dir_t object that we're currently spooling out */
@@ -1850,6 +1853,10 @@
int UseBridges; /**< Boolean: should we start all circuits with a bridge? */
config_line_t *Bridges; /**< List of bootstrap bridge addresses. */
+ /** Boolean: if we know the bridge's digest, should we get new
+ * descriptors from the bridge authorities or from the bridge itself? */
+ int UpdateBridgesFromAuthority;
+
int AvoidDiskWrites; /**< Boolean: should we never cache things to disk?
* Not used yet. */
int ClientOnly; /**< Boolean: should we never evolve into a server role? */
@@ -2210,6 +2217,10 @@
const char *question, char **answer);
void entry_guards_free_all(void);
+void clear_bridge_list(void);
+void bridge_add_from_config(uint32_t addr, uint16_t port, char *digest);
+void learn_bridge_descriptors(void);
+
/********************************* circuitlist.c ***********************/
circuit_t * _circuit_get_global_list(void);
@@ -2640,10 +2651,11 @@
void directory_post_to_dirservers(uint8_t purpose, authority_type_t type,
const char *payload,
size_t payload_len, size_t extrainfo_len);
-void directory_get_from_dirserver(uint8_t purpose, const char *resource,
+void directory_get_from_dirserver(uint8_t dir_purpose, const char *resource,
int retry_if_no_servers);
void directory_initiate_command_routerstatus(routerstatus_t *status,
- uint8_t purpose,
+ uint8_t dir_purpose,
+ uint8_t router_purpose,
int anonymized_connection,
const char *resource,
const char *payload,
@@ -2659,8 +2671,8 @@
void connection_dir_request_failed(dir_connection_t *conn);
void directory_initiate_command(const char *address, uint32_t addr,
uint16_t or_port, uint16_t dir_port,
- int supports_begindir,
- const char *digest, uint8_t purpose,
+ int supports_begindir, const char *digest,
+ uint8_t dir_purpose, uint8_t router_purpose,
int anonymized_connection,
const char *resource,
const char *payload, size_t payload_len);
@@ -3202,6 +3214,7 @@
} trusted_dir_server_t;
int router_reload_router_list(void);
+int get_n_authorities(authority_type_t type);
int router_reload_networkstatus(void);
smartlist_t *router_get_trusted_dir_servers(void);
routerstatus_t *router_pick_directory_server(int requireother,
@@ -3274,7 +3287,8 @@
const char **msg);
void router_load_routers_from_string(const char *s, const char *eos,
saved_location_t saved_location,
- smartlist_t *requested_fingerprints);
+ smartlist_t *requested_fingerprints,
+ uint8_t purpose);
void router_load_extrainfo_from_string(const char *s, const char *eos,
saved_location_t saved_location,
smartlist_t *requested_fps);
Modified: tor/trunk/src/or/router.c
===================================================================
--- tor/trunk/src/or/router.c 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/router.c 2007-06-10 07:34:21 UTC (rev 10548)
@@ -614,6 +614,7 @@
me->or_port, me->dir_port,
0, me->cache_info.identity_digest,
DIR_PURPOSE_FETCH_SERVERDESC,
+ ROUTER_PURPOSE_GENERAL,
1, "authority", NULL, 0);
control_event_server_status(LOG_NOTICE,
Modified: tor/trunk/src/or/routerlist.c
===================================================================
--- tor/trunk/src/or/routerlist.c 2007-06-10 00:30:14 UTC (rev 10547)
+++ tor/trunk/src/or/routerlist.c 2007-06-10 07:34:21 UTC (rev 10548)
@@ -109,7 +109,7 @@
/** Return the number of directory authorities whose type matches some bit set
* in <b>type</b> */
-static INLINE int
+INLINE int
get_n_authorities(authority_type_t type)
{
int n = 0;
@@ -549,7 +549,8 @@
else
router_load_routers_from_string((*mmap_ptr)->data,
(*mmap_ptr)->data+(*mmap_ptr)->size,
- SAVED_IN_CACHE, NULL);
+ SAVED_IN_CACHE, NULL,
+ ROUTER_PURPOSE_GENERAL);
}
tor_snprintf(fname, fname_len, "%s"PATH_SEPARATOR"%s.new",
@@ -560,7 +561,8 @@
if (extrainfo)
router_load_extrainfo_from_string(contents, NULL,SAVED_IN_JOURNAL, NULL);
else
- router_load_routers_from_string(contents, NULL, SAVED_IN_JOURNAL, NULL);
+ router_load_routers_from_string(contents, NULL, SAVED_IN_JOURNAL, NULL,
+ ROUTER_PURPOSE_GENERAL);
stats->journal_len = (size_t) st.st_size;
tor_free(contents);
}
@@ -2788,7 +2790,8 @@
void
router_load_routers_from_string(const char *s, const char *eos,
saved_location_t saved_location,
- smartlist_t *requested_fingerprints)
+ smartlist_t *requested_fingerprints,
+ uint8_t purpose)
{
smartlist_t *routers = smartlist_create(), *changed = smartlist_create();
char fp[HEX_DIGEST_LEN+1];
@@ -2821,6 +2824,10 @@
}
}
+ ri->purpose = purpose;
+ if (purpose != ROUTER_PURPOSE_GENERAL)
+ ri->cache_info.do_not_cache = 1;
+
if (router_add_to_routerlist(ri, &msg, from_cache, !from_cache) >= 0)
smartlist_add(changed, ri);
});
@@ -3340,6 +3347,10 @@
if (connection_get_by_type_addr_port_purpose(
CONN_TYPE_DIR, ds->addr, ds->dir_port,
DIR_PURPOSE_FETCH_NETWORKSTATUS)) {
+ /* XXX020 the above dir_port won't be accurate if we're
+ * doing a tunneled conn. In that case it should be or_port.
+ * How to guess from here? Maybe make the function less general
+ * and have it know that it's looking for dir conns. -RD */
/* We are already fetching this one. */
continue;
}
@@ -3348,6 +3359,7 @@
strlcat(resource, ".z", sizeof(resource));
directory_initiate_command_routerstatus(
&ds->fake_status.status, DIR_PURPOSE_FETCH_NETWORKSTATUS,
+ ROUTER_PURPOSE_GENERAL,
0, /* Not private */
resource,
NULL, 0 /* No payload. */);
@@ -4365,6 +4377,7 @@
if (source) {
/* We know which authority we want. */
directory_initiate_command_routerstatus(source, purpose,
+ ROUTER_PURPOSE_GENERAL,
0, /* not private */
resource, NULL, 0);
} else {
More information about the tor-commits
mailing list