summaryrefslogtreecommitdiff
path: root/src/or/directory.c
diff options
context:
space:
mode:
authorAndrea Shepard <andrea@torproject.org>2013-05-09 04:56:54 -0700
committerAndrea Shepard <andrea@torproject.org>2013-05-09 10:55:01 -0700
commitfddb814feaa3d0091df03b26fa709cfba55312ed (patch)
treea80560b8e77ab80ac5f88136521bd618253d00ff /src/or/directory.c
parentd5bd4a4763dfa74572ce6ed0b565315c43ff9f87 (diff)
downloadtor-fddb814feaa3d0091df03b26fa709cfba55312ed.tar.gz
tor-fddb814feaa3d0091df03b26fa709cfba55312ed.zip
When downloading certificates, distinguish requesting by identity digest from requesting by ID digest, signing key pair; fixes bug 5595
Diffstat (limited to 'src/or/directory.c')
-rw-r--r--src/or/directory.c69
1 files changed, 55 insertions, 14 deletions
diff --git a/src/or/directory.c b/src/or/directory.c
index f235bf3b41..8dd5a7cdc8 100644
--- a/src/or/directory.c
+++ b/src/or/directory.c
@@ -809,13 +809,34 @@ connection_dir_download_cert_failed(dir_connection_t *conn, int status)
if (!conn->requested_resource)
return;
failed = smartlist_new();
- dir_split_resource_into_fingerprints(conn->requested_resource+3,
- failed, NULL, DSR_HEX);
- SMARTLIST_FOREACH(failed, char *, cp,
- {
- authority_cert_dl_failed(cp, status);
- tor_free(cp);
- });
+ /*
+ * We have two cases download by fingerprint (resource starts
+ * with "fp/") or download by fingerprint/signing key pair
+ * (resource starts with "fp-sk/").
+ */
+ if (!strcmpstart(conn->requested_resource, "fp/")) {
+ /* Download by fingerprint case */
+ dir_split_resource_into_fingerprints(conn->requested_resource + 3,
+ failed, NULL, DSR_HEX);
+ SMARTLIST_FOREACH_BEGIN(failed, char *, cp) {
+ /* Null signing key digest indicates download by fp only */
+ authority_cert_dl_failed(cp, NULL, status);
+ tor_free(cp);
+ } SMARTLIST_FOREACH_END(cp);
+ } else if (!strcmpstart(conn->requested_resource, "fp-sk/")) {
+ /* Download by (fp,sk) pairs */
+ dir_split_resource_into_fingerprint_pairs(conn->requested_resource + 5,
+ failed);
+ SMARTLIST_FOREACH_BEGIN(failed, fp_pair_t *, cp) {
+ authority_cert_dl_failed(cp->first, cp->second, status);
+ tor_free(cp);
+ } SMARTLIST_FOREACH_END(cp);
+ } else {
+ log_warn(LD_DIR,
+ "Don't know what to do with failure for cert fetch %s",
+ conn->requested_resource);
+ }
+
smartlist_free(failed);
update_certificate_downloads(time(NULL));
@@ -1589,6 +1610,7 @@ connection_dir_client_reached_eof(dir_connection_t *conn)
conn->_base.purpose == DIR_PURPOSE_FETCH_MICRODESC);
int was_compressed=0;
time_t now = time(NULL);
+ int src_code;
switch (connection_fetch_from_buf_http(TO_CONN(conn),
&headers, MAX_HEADERS_SIZE,
@@ -1857,14 +1879,33 @@ connection_dir_client_reached_eof(dir_connection_t *conn)
}
log_info(LD_DIR,"Received authority certificates (size %d) from server "
"'%s:%d'", (int)body_len, conn->_base.address, conn->_base.port);
- if (trusted_dirs_load_certs_from_string(body, 0, 1)<0) {
- log_warn(LD_DIR, "Unable to parse fetched certificates");
- /* if we fetched more than one and only some failed, the successful
- * ones got flushed to disk so it's safe to call this on them */
- connection_dir_download_cert_failed(conn, status_code);
+ /*
+ * Tell trusted_dirs_load_certs_from_string() whether it was by fp
+ * or fp-sk pair.
+ */
+ src_code = -1;
+ if (!strcmpstart(conn->requested_resource, "fp/")) {
+ src_code = TRUSTED_DIRS_CERTS_SRC_DL_BY_ID_DIGEST;
+ } else if (!strcmpstart(conn->requested_resource, "fp-sk/")) {
+ src_code = TRUSTED_DIRS_CERTS_SRC_DL_BY_ID_SK_DIGEST;
+ }
+
+ if (src_code != -1) {
+ if (trusted_dirs_load_certs_from_string(body, src_code, 1)<0) {
+ log_warn(LD_DIR, "Unable to parse fetched certificates");
+ /* if we fetched more than one and only some failed, the successful
+ * ones got flushed to disk so it's safe to call this on them */
+ connection_dir_download_cert_failed(conn, status_code);
+ } else {
+ directory_info_has_arrived(now, 0);
+ log_info(LD_DIR, "Successfully loaded certificates from fetch.");
+ }
} else {
- directory_info_has_arrived(now, 0);
- log_info(LD_DIR, "Successfully loaded certificates from fetch.");
+ log_warn(LD_DIR,
+ "Couldn't figure out what to do with fetched certificates for "
+ "unknown resource %s",
+ conn->requested_resource);
+ connection_dir_download_cert_failed(conn, status_code);
}
}
if (conn->_base.purpose == DIR_PURPOSE_FETCH_STATUS_VOTE) {