diff options
author | Nick Mathewson <nickm@torproject.org> | 2013-06-13 09:40:32 -0400 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2013-06-13 09:40:32 -0400 |
commit | 25dddf7a8f30699242b52fce115f29401f63ee9c (patch) | |
tree | 1b353ff92a3f30b3e8a94804f580b223555ac906 | |
parent | 74a534be15a26cddb8b134757416a7550072f44b (diff) | |
parent | e602c4031b57f0780661ce0473a5e30d187d385c (diff) | |
download | tor-25dddf7a8f30699242b52fce115f29401f63ee9c.tar.gz tor-25dddf7a8f30699242b52fce115f29401f63ee9c.zip |
Merge remote-tracking branch 'public/bug8822' into maint-0.2.4
-rw-r--r-- | changes/bug8822 | 5 | ||||
-rw-r--r-- | src/or/control.c | 6 | ||||
-rw-r--r-- | src/or/dirserv.c | 2 | ||||
-rw-r--r-- | src/or/microdesc.c | 26 |
4 files changed, 30 insertions, 9 deletions
diff --git a/changes/bug8822 b/changes/bug8822 new file mode 100644 index 0000000000..c6787afe06 --- /dev/null +++ b/changes/bug8822 @@ -0,0 +1,5 @@ + o Major bugfixes (windows): + - Prevent failures on Windows Vista and later when rebuilding the + microdescriptor cache. Diagnosed by Robert Ransom. Fixes bug 8822; + bugfix on 0.2.4.12-alpha. + diff --git a/src/or/control.c b/src/or/control.c index 88bd00b5e3..a88de12d69 100644 --- a/src/or/control.c +++ b/src/or/control.c @@ -1711,8 +1711,7 @@ getinfo_helper_dir(control_connection_t *control_conn, const node_t *node = node_get_by_hex_id(question+strlen("md/id/")); const microdesc_t *md = NULL; if (node) md = node->md; - if (md) { - tor_assert(md->body); + if (md && md->body) { *answer = tor_strndup(md->body, md->bodylen); } } else if (!strcmpstart(question, "md/name/")) { @@ -1722,8 +1721,7 @@ getinfo_helper_dir(control_connection_t *control_conn, /* XXXX duplicated code */ const microdesc_t *md = NULL; if (node) md = node->md; - if (md) { - tor_assert(md->body); + if (md && md->body) { *answer = tor_strndup(md->body, md->bodylen); } } else if (!strcmpstart(question, "desc-annotations/id/")) { diff --git a/src/or/dirserv.c b/src/or/dirserv.c index 8f6d9ec438..3e46153a55 100644 --- a/src/or/dirserv.c +++ b/src/or/dirserv.c @@ -3981,7 +3981,7 @@ connection_dirserv_add_microdescs_to_outbuf(dir_connection_t *conn) char *fp256 = smartlist_pop_last(conn->fingerprint_stack); microdesc_t *md = microdesc_cache_lookup_by_digest256(cache, fp256); tor_free(fp256); - if (!md) + if (!md || !md->body) continue; if (conn->zlib_state) { /* XXXX024 This 'last' business should actually happen on the last diff --git a/src/or/microdesc.c b/src/or/microdesc.c index d9955c7b49..05e3b41815 100644 --- a/src/or/microdesc.c +++ b/src/or/microdesc.c @@ -75,6 +75,10 @@ dump_microdescriptor(int fd, microdesc_t *md, size_t *annotation_len_out) { ssize_t r = 0; size_t written; + if (md->body == NULL) { + *annotation_len_out = 0; + return 0; + } /* XXXX drops unknown annotations. */ if (md->last_listed) { char buf[ISO_TIME_LEN+1]; @@ -447,7 +451,7 @@ microdesc_cache_rebuild(microdesc_cache_t *cache, int force) HT_FOREACH(mdp, microdesc_map, &cache->map) { microdesc_t *md = *mdp; size_t annotation_len; - if (md->no_save) + if (md->no_save || !md->body) continue; size = dump_microdescriptor(fd, md, &annotation_len); @@ -474,15 +478,29 @@ microdesc_cache_rebuild(microdesc_cache_t *cache, int force) smartlist_add(wrote, md); } + /* We must do this unmap _before_ we call finish_writing_to_file(), or + * windows will not actually replace the file. */ + if (cache->cache_content) + tor_munmap_file(cache->cache_content); + if (finish_writing_to_file(open_file) < 0) { log_warn(LD_DIR, "Error rebuilding microdescriptor cache: %s", strerror(errno)); + /* Okay. Let's prevent from making things worse elsewhere. */ + cache->cache_content = NULL; + HT_FOREACH(mdp, microdesc_map, &cache->map) { + microdesc_t *md = *mdp; + if (md->saved_location == SAVED_IN_CACHE) { + md->off = 0; + md->saved_location = SAVED_NOWHERE; + md->body = NULL; + md->bodylen = 0; + md->no_save = 1; + } + } return -1; } - if (cache->cache_content) - tor_munmap_file(cache->cache_content); - cache->cache_content = tor_mmap_file(cache->cache_fname); if (!cache->cache_content && smartlist_len(wrote)) { |