|
@@ -293,6 +293,7 @@ networkstatus_compute_consensus(smartlist_t *votes,
|
|
|
int j;
|
|
|
SMARTLIST_FOREACH(votes, networkstatus_vote_t *, v,
|
|
|
{
|
|
|
+ tor_assert(v->is_vote);
|
|
|
smartlist_add(va_times, &v->valid_after);
|
|
|
smartlist_add(fu_times, &v->fresh_until);
|
|
|
smartlist_add(vu_times, &v->valid_until);
|
|
@@ -629,3 +630,64 @@ networkstatus_compute_consensus(smartlist_t *votes,
|
|
|
return result;
|
|
|
}
|
|
|
|
|
|
+
|
|
|
+int
|
|
|
+networkstatus_check_consensus_signature(networkstatus_vote_t *consensus)
|
|
|
+{
|
|
|
+ int n_good = 0;
|
|
|
+ int n_missing_key = 0;
|
|
|
+ int n_bad = 0;
|
|
|
+ int n_unknown = 0;
|
|
|
+
|
|
|
+ tor_assert(! consensus->is_vote);
|
|
|
+
|
|
|
+ SMARTLIST_FOREACH(consensus->voters, networkstatus_voter_info_t *, voter,
|
|
|
+ {
|
|
|
+ trusted_dir_server_t *ds =
|
|
|
+ trusteddirserver_get_by_v3_auth_digest(voter->identity_digest);
|
|
|
+ if (!ds) {
|
|
|
+ ++n_unknown;
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+ if (voter->pending_signature) {
|
|
|
+ char d[DIGEST_LEN];
|
|
|
+ char *signed_digest;
|
|
|
+ size_t signed_digest_len;
|
|
|
+ tor_assert(!voter->good_signature && !voter->bad_signature);
|
|
|
+ if (!ds->v3_cert) {
|
|
|
+ ++n_missing_key;
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+
|
|
|
+ crypto_pk_get_digest(ds->v3_cert->signing_key, d);
|
|
|
+ if (memcmp(voter->signing_key_digest, d, DIGEST_LEN)) {
|
|
|
+ ++n_missing_key;
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+ signed_digest_len = crypto_pk_keysize(ds->v3_cert->signing_key);
|
|
|
+ signed_digest = tor_malloc(signed_digest_len);
|
|
|
+ if (crypto_pk_public_checksig(ds->v3_cert->signing_key,
|
|
|
+ signed_digest,
|
|
|
+ voter->pending_signature,
|
|
|
+ voter->pending_signature_len) != DIGEST_LEN ||
|
|
|
+ memcmp(signed_digest, consensus->networkstatus_digest, DIGEST_LEN)) {
|
|
|
+ log_warn(LD_DIR, "Got a bad signature.");
|
|
|
+ voter->bad_signature = 1;
|
|
|
+ } else {
|
|
|
+ voter->good_signature = 1;
|
|
|
+ }
|
|
|
+ tor_free(voter->pending_signature);
|
|
|
+ }
|
|
|
+ if (voter->good_signature)
|
|
|
+ ++n_good;
|
|
|
+ else if (voter->bad_signature)
|
|
|
+ ++n_bad;
|
|
|
+ else
|
|
|
+ tor_assert(0);
|
|
|
+ });
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|