[tor-commits] [tor/master] Allow conflicts to occur in keypinning journal

nickm at torproject.org nickm at torproject.org
Thu Sep 24 15:29:44 UTC 2015


commit c5e87e33c7a3bf0f3d6b289814d303bcb4c63fe2
Author: Nick Mathewson <nickm at torproject.org>
Date:   Wed Sep 23 10:44:38 2015 -0400

    Allow conflicts to occur in keypinning journal
    
    When we find a conflict in the keypinning journal, treat the new
    entry as superseding all old entries that overlap either of its
    keys.
    
    Also add a (not-yet-used) configuration option to disable keypinning
    enforcement.
---
 src/or/config.c        |    1 +
 src/or/keypin.c        |   42 ++++++++++++++++++++++++++++++++----------
 src/or/or.h            |    1 +
 src/test/test_keypin.c |   10 +++++-----
 4 files changed, 39 insertions(+), 15 deletions(-)

diff --git a/src/or/config.c b/src/or/config.c
index 44fb4ec..fa860af 100644
--- a/src/or/config.c
+++ b/src/or/config.c
@@ -162,6 +162,7 @@ static config_var_t option_vars_[] = {
   V(AuthDirInvalidCCs,           CSV,      ""),
   V(AuthDirFastGuarantee,        MEMUNIT,  "100 KB"),
   V(AuthDirGuardBWGuarantee,     MEMUNIT,  "2 MB"),
+  V(AuthDirPinKeys,              BOOL,     "0"),
   V(AuthDirReject,               LINELIST, NULL),
   V(AuthDirRejectCCs,            CSV,      ""),
   OBSOLETE("AuthDirRejectUnlisted"),
diff --git a/src/or/keypin.c b/src/or/keypin.c
index ebe83b3..cab6c9d 100644
--- a/src/or/keypin.c
+++ b/src/or/keypin.c
@@ -321,19 +321,41 @@ keypin_load_journal_impl(const char *data, size_t size)
       continue;
     }
 
-    const keypin_ent_t *ent2;
-    if ((ent2 = HT_FIND(rsamap, &the_rsa_map, ent))) {
-      if (fast_memeq(ent2->ed25519_key, ent->ed25519_key, DIGEST256_LEN)) {
-        ++n_duplicates;
-      } else {
-        ++n_conflicts;
-      }
+    keypin_ent_t *ent2 = HT_FIND(rsamap, &the_rsa_map, ent);
+    keypin_ent_t *ent3 = HT_FIND(edmap, &the_ed_map, ent);
+    if (ent2 &&
+        fast_memeq(ent2->ed25519_key, ent->ed25519_key, DIGEST256_LEN)) {
+      /* We already have this mapping stored. Ignore it. */
       tor_free(ent);
+      ++n_duplicates;
       continue;
-    } else if (HT_FIND(edmap, &the_ed_map, ent)) {
-      tor_free(ent);
+    } else if (ent2 || ent3) {
+      /* We have a conflict. (If we had no entry, we would have ent2 == ent3
+       * == NULL. If we had a non-conflicting duplicate, we would have found
+       * it above.)
+       *
+       * We respond by having this entry (ent) supersede all entries that it
+       * contradicts (ent2 and/or ent3). In other words, if we receive
+       * <rsa,ed>, we remove all <rsa,ed'> and all <rsa',ed>, for rsa'!=rsa
+       * and ed'!= ed.
+       */
+      const keypin_ent_t *t;
+      if (ent2) {
+        t = HT_REMOVE(rsamap, &the_rsa_map, ent2);
+        tor_assert(ent2 == t);
+        t = HT_REMOVE(edmap, &the_ed_map, ent2);
+        tor_assert(ent2 == t);
+      }
+      if (ent3 && ent2 != ent3) {
+        t = HT_REMOVE(rsamap, &the_rsa_map, ent3);
+        tor_assert(ent3 == t);
+        t = HT_REMOVE(edmap, &the_ed_map, ent3);
+        tor_assert(ent3 == t);
+        tor_free(ent3);
+      }
+      tor_free(ent2);
       ++n_conflicts;
-      continue;
+      /* Fall through */
     }
 
     keypin_add_entry_to_map(ent);
diff --git a/src/or/or.h b/src/or/or.h
index bec39b2..4496cbc 100644
--- a/src/or/or.h
+++ b/src/or/or.h
@@ -3790,6 +3790,7 @@ typedef struct {
                                      * number of servers per IP address shared
                                      * with an authority. */
   int AuthDirHasIPv6Connectivity; /**< Boolean: are we on IPv6?  */
+  int AuthDirPinKeys; /**< Boolean: Do we enforce key-pinning? */
 
   /** If non-zero, always vote the Fast flag for any relay advertising
    * this amount of capacity or more. */
diff --git a/src/test/test_keypin.c b/src/test/test_keypin.c
index afd4ca2..033578c 100644
--- a/src/test/test_keypin.c
+++ b/src/test/test_keypin.c
@@ -108,21 +108,21 @@ test_keypin_parse_file(void *arg)
     ;
 
   tt_int_op(0, ==, keypin_load_journal_impl(data2, strlen(data2)));
-  tt_int_op(11, ==, smartlist_len(mock_addent_got));
+  tt_int_op(13, ==, smartlist_len(mock_addent_got));
   ent = smartlist_get(mock_addent_got, 9);
   tt_mem_op(ent->rsa_id, ==, "\"You have made a goo", 20);
   tt_mem_op(ent->ed25519_key, ==, "d beginning.\" But no more. Wizar", 32);
 
-  ent = smartlist_get(mock_addent_got, 10);
+  ent = smartlist_get(mock_addent_got, 12);
   tt_mem_op(ent->rsa_id, ==, "ds speak truth, and ", 20);
-  tt_mem_op(ent->ed25519_key, ==, "it was true that all the master\n", 32);
+  tt_mem_op(ent->ed25519_key, ==, "it was tru\xa5 that all the master\n", 32);
 
   /* File truncated before NL */
   const char data3[] =
     "Tm8gZHJhZ29uIGNhbiByZXNpc3Q IHRoZSBmYXNjaW5hdGlvbiBvZiByaWRkbGluZyB0YWw";
   tt_int_op(0, ==, keypin_load_journal_impl(data3, strlen(data3)));
-  tt_int_op(12, ==, smartlist_len(mock_addent_got));
-  ent = smartlist_get(mock_addent_got, 11);
+  tt_int_op(14, ==, smartlist_len(mock_addent_got));
+  ent = smartlist_get(mock_addent_got, 13);
   tt_mem_op(ent->rsa_id, ==, "No dragon can resist", 20);
   tt_mem_op(ent->ed25519_key, ==, " the fascination of riddling tal", 32);
 





More information about the tor-commits mailing list