From 1582adabbb13871bcf6f91be4fa8523aeb36f79a Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 14 Feb 2017 12:21:31 -0500 Subject: Change approach to preventing duplicate guards. Previously I'd made a bad assumption in the implementation of prop271 in 0.3.0.1-alpha: I'd assumed that there couldn't be two guards with the same identity. That's true for non-bridges, but in the bridge case, we allow two bridges to have the same ID if they have different addr:port combinations -- in order to have the same bridge ID running multiple PTs. Fortunately, this assumption wasn't deeply ingrained: we stop enforcing the "one guard per ID" rule in the bridge case, and instead enforce "one guard per ". We also needed to tweak our implementation of get_bridge_info_for_guard, since it made the same incorrect assumption. Fixes bug 21027; bugfix on 0.3.0.1-alpha. --- src/or/bridges.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) (limited to 'src/or/bridges.c') diff --git a/src/or/bridges.c b/src/or/bridges.c index 8b37f412ea..f766931b46 100644 --- a/src/or/bridges.c +++ b/src/or/bridges.c @@ -199,6 +199,33 @@ get_configured_bridge_by_addr_port_digest(const tor_addr_t *addr, return NULL; } +/** + * As get_configured_bridge_by_addr_port, but require that the + * address match addr:port, and that the ID digest match + * digest. (The other function will ignore the address if the + * digest matches.) + */ +bridge_info_t * +get_configured_bridge_by_exact_addr_port_digest(const tor_addr_t *addr, + uint16_t port, + const char *digest) +{ + if (!bridge_list) + return NULL; + SMARTLIST_FOREACH_BEGIN(bridge_list, bridge_info_t *, bridge) { + if (!tor_addr_compare(&bridge->addr, addr, CMP_EXACT) && + bridge->port == port) { + + if (digest && tor_memeq(bridge->identity, digest, DIGEST_LEN)) + return bridge; + else if (!digest) + return bridge; + } + + } SMARTLIST_FOREACH_END(bridge); + return NULL; +} + /** If we have a bridge configured whose digest matches digest, or a * bridge with no known digest whose address matches addr:port, * return 1. Else return 0. If digest is NULL, check for -- cgit v1.2.3-54-g00ecf