diff options
author | Roger Dingledine <arma@torproject.org> | 2002-08-23 03:35:44 +0000 |
---|---|---|
committer | Roger Dingledine <arma@torproject.org> | 2002-08-23 03:35:44 +0000 |
commit | 08adaa4b4673024b07913104ef00f641b829e4b5 (patch) | |
tree | f8d8b3cc359c7ace4a12af58a486fbecedc5fc38 /src | |
parent | 01aadefbfc7dbd99ddaff922b897996b768cf2f9 (diff) | |
download | tor-08adaa4b4673024b07913104ef00f641b829e4b5.tar tor-08adaa4b4673024b07913104ef00f641b829e4b5.tar.gz |
cleaned up new_route()
now it deals gracefully with too few connected routers (i think)
svn:r77
Diffstat (limited to 'src')
-rw-r--r-- | src/or/connection.c | 4 | ||||
-rw-r--r-- | src/or/main.c | 4 | ||||
-rw-r--r-- | src/or/onion.c | 104 |
3 files changed, 68 insertions, 44 deletions
diff --git a/src/or/connection.c b/src/or/connection.c index ed00c7507..733c96734 100644 --- a/src/or/connection.c +++ b/src/or/connection.c @@ -194,7 +194,7 @@ int connection_handle_listener_read(connection_t *conn, int new_type, int new_st } log(LOG_DEBUG,"Connection accepted on socket %d.",news); - fcntl(news, F_SETFL, O_NONBLOCK); /* set s to non-blocking */ + fcntl(news, F_SETFL, O_NONBLOCK); /* set news to non-blocking */ newconn = connection_new(new_type); newconn->s = news; @@ -207,7 +207,7 @@ int connection_handle_listener_read(connection_t *conn, int new_type, int new_st /* learn things from parent, so we can perform auth */ memcpy(&newconn->local,&conn->local,sizeof(struct sockaddr_in)); newconn->prkey = conn->prkey; -// newconn->address = strdup(get_string_from_remote()) FIXME ; + newconn->address = strdup(inet_ntoa(*(struct in_addr *)&remote.sin_addr.s_addr)); /* remember the remote address */ if(connection_add(newconn) < 0) { /* no space, forget it */ connection_free(newconn); diff --git a/src/or/main.c b/src/or/main.c index 88e8c16c9..1c5866180 100644 --- a/src/or/main.c +++ b/src/or/main.c @@ -108,7 +108,7 @@ connection_t *connection_twin_get_by_addr_port(uint32_t addr, uint16_t port) { /* first check if it's there exactly */ conn = connection_exact_get_by_addr_port(addr,port); if(conn && connection_state_is_open(conn)) { - log(LOG_DEBUG,"connection_twin_get_by_addr_port(): Found exact match."); + log(LOG_INFO,"connection_twin_get_by_addr_port(): Found exact match."); return conn; } @@ -122,7 +122,7 @@ connection_t *connection_twin_get_by_addr_port(uint32_t addr, uint16_t port) { conn = connection_array[i]; assert(conn); if(connection_state_is_open(conn) && !pkey_cmp(conn->pkey, router->pkey)) { - log(LOG_DEBUG,"connection_twin_get_by_addr_port(): Found twin (%s).",conn->address); + log(LOG_INFO,"connection_twin_get_by_addr_port(): Found twin (%s).",conn->address); return conn; } } diff --git a/src/or/onion.c b/src/or/onion.c index 12971d098..ed8198019 100644 --- a/src/or/onion.c +++ b/src/or/onion.c @@ -95,60 +95,84 @@ int chooselen(double cw) unsigned int *new_route(double cw, routerinfo_t **rarray, size_t rarray_len, size_t *rlen) { int routelen = 0; - int i = 0; + int i, j; + int num_acceptable_routers = 0; int retval = 0; unsigned int *route = NULL; unsigned int oldchoice, choice; assert((cw >= 0) && (cw < 1) && (rarray) && (rlen) ); /* valid parameters */ - routelen = chooselen(cw); - if (routelen == -1) - { - log(LOG_ERR,"Choosing route length failed."); - return NULL; + routelen = chooselen(cw); + if (routelen == -1) { + log(LOG_ERR,"Choosing route length failed."); + return NULL; + } + log(LOG_DEBUG,"new_route(): Chosen route length %d.",routelen); + + for(i=0;i<rarray_len;i++) { + log(LOG_DEBUG,"Contemplating whether router %d is any good...",i); + if(!connection_exact_get_by_addr_port(rarray[i]->addr, rarray[i]->or_port)) { + log(LOG_DEBUG,"Nope, %d is not connected.",i); + goto next_i_loop; + } + for(j=0;j<i;j++) { + if(!pkey_cmp(rarray[i]->pkey, rarray[j]->pkey)) { + /* these guys are twins. so we've already counted him. */ + log(LOG_DEBUG,"Nope, %d is a twin of %d.",i,j); + goto next_i_loop; + } } - log(LOG_DEBUG,"new_route(): Chosen route length %u.",routelen); + num_acceptable_routers++; + log(LOG_DEBUG,"I like %d. num_acceptable_routers now %d.",i, num_acceptable_routers); + next_i_loop: + } + + if(num_acceptable_routers < routelen) { + log(LOG_DEBUG,"new_route(): Cutting routelen from %d to %d.",routelen, num_acceptable_routers); + routelen = num_acceptable_routers; + } - /* FIXME need to figure out how many routers we can actually choose from. - * We can get into an infinite loop if there are too few. */ - - /* allocate memory for the new route */ - route = (unsigned int *)malloc(routelen * sizeof(unsigned int)); - if (!route) - { - log(LOG_ERR,"Memory allocation failed."); + if(routelen < 1) { + log(LOG_ERR,"new_route(): Didn't find any acceptable routers. Failing."); + return NULL; + } + + /* allocate memory for the new route */ + route = (unsigned int *)malloc(routelen * sizeof(unsigned int)); + if (!route) { + log(LOG_ERR,"Memory allocation failed."); + return NULL; + } + + oldchoice = rarray_len; + for(i=0;i<routelen;i++) { + log(LOG_DEBUG,"new_route(): Choosing hop %u.",i); + retval = crypto_pseudo_rand(sizeof(unsigned int),(unsigned char *)&choice); + if (retval) { + free((void *)route); return NULL; } - - oldchoice = rarray_len; - for(i=0;i<routelen;i++) - { - log(LOG_DEBUG,"new_route() : Choosing hop %u.",i); - retval = crypto_pseudo_rand(sizeof(unsigned int),(unsigned char *)&choice); - if (retval) - { - free((void *)route); - return NULL; - } + choice = choice % (rarray_len); + log(LOG_DEBUG,"new_route(): Contemplating router %u.",choice); + while(choice == oldchoice || + (oldchoice < rarray_len && !pkey_cmp(rarray[choice]->pkey, rarray[oldchoice]->pkey)) || + !connection_twin_get_by_addr_port(rarray[choice]->addr, rarray[choice]->or_port)) { + /* Same router as last choice, or router twin, + * or no routers with that key are connected to us. + * Try again. */ + log(LOG_DEBUG,"new_route(): Picked a router %d that won't work as next hop.",choice); + choice++; choice = choice % (rarray_len); - log(LOG_DEBUG,"new_route() : Chosen router %u.",choice); - if (choice == oldchoice || - (oldchoice < rarray_len && !pkey_cmp(rarray[choice]->pkey, rarray[oldchoice]->pkey)) || - !connection_twin_get_by_addr_port(rarray[choice]->addr, rarray[choice]->or_port)) { - /* Same router as last choice, or router twin, - * or no routers with that key are connected to us. - * Try again. */ - i--; - continue; - } - oldchoice = choice; - route[i] = choice; } + log(LOG_DEBUG,"new_route(): Chosen router %u for hop %u.",choice,i); + oldchoice = choice; + route[i] = choice; + } - *rlen = routelen; - return route; + *rlen = routelen; + return route; } /* creates a new onion from route, stores it and its length into bufp and lenp respectively */ |