aboutsummaryrefslogtreecommitdiff
path: root/src/or/hs_common.c
diff options
context:
space:
mode:
authorDavid Goulet <dgoulet@torproject.org>2017-04-18 15:06:44 -0400
committerNick Mathewson <nickm@torproject.org>2017-08-08 20:29:33 -0400
commit267bc7bc3b574f3e60d7836fde5a24652e3ac9c2 (patch)
treede4b64fa9ea873e5694a67bc6c4b74b816a9ffe4 /src/or/hs_common.c
parent77b279c35c5ecf83c045f9c1d613544d958aef81 (diff)
downloadtor-267bc7bc3b574f3e60d7836fde5a24652e3ac9c2.tar.gz
tor-267bc7bc3b574f3e60d7836fde5a24652e3ac9c2.zip
prop224: Build hsdir index for node_t
This hsdir index value is used to give an index value to all node_t (relays) that supports HSDir v3. An index value is then computed using the blinded key to know where to fetch/upload the service descriptor from/to. To avoid computing that index value everytime the client/service needs it, we do that everytime we get a new consensus which then doesn't change until the next one. The downside is that we need to sort them once we need to compute the set of responsible HSDir. Finally, the "hs_index" function is also added but not used. It will be used in later commits to compute which node_t is a responsible HSDir for the service we want to fetch/upload the descriptor. Signed-off-by: David Goulet <dgoulet@torproject.org>
Diffstat (limited to 'src/or/hs_common.c')
-rw-r--r--src/or/hs_common.c113
1 files changed, 113 insertions, 0 deletions
diff --git a/src/or/hs_common.c b/src/or/hs_common.c
index 571f4c5178..0e3562de87 100644
--- a/src/or/hs_common.c
+++ b/src/or/hs_common.c
@@ -20,6 +20,7 @@
#include "hs_service.h"
#include "rendcommon.h"
#include "rendservice.h"
+#include "shared_random.h"
/* Ed25519 Basepoint value. Taken from section 5 of
* https://tools.ietf.org/html/draft-josefsson-eddsa-ed25519-03 */
@@ -369,6 +370,25 @@ rend_data_get_pk_digest(const rend_data_t *rend_data, size_t *len_out)
}
}
+/* Using the given time period number, compute the disaster shared random
+ * value and put it in srv_out. It MUST be at least DIGEST256_LEN bytes. */
+static void
+get_disaster_srv(uint64_t time_period_num, uint8_t *srv_out)
+{
+ crypto_digest_t *digest;
+
+ tor_assert(srv_out);
+
+ digest = crypto_digest256_new(DIGEST_SHA3_256);
+ /* Setup payload: H("shared-random-disaster" | INT_8(period_num)) */
+ crypto_digest_add_bytes(digest, HS_SRV_DISASTER_PREFIX,
+ HS_SRV_DISASTER_PREFIX_LEN);
+ crypto_digest_add_bytes(digest, (const char *) &time_period_num,
+ sizeof(time_period_num));
+ crypto_digest_get_digest(digest, (char *) srv_out, DIGEST256_LEN);
+ crypto_digest_free(digest);
+}
+
/* When creating a blinded key, we need a parameter which construction is as
* follow: H(pubkey | [secret] | ed25519-basepoint | nonce).
*
@@ -744,6 +764,99 @@ hs_service_requires_uptime_circ(const smartlist_t *ports)
return 0;
}
+/* Build hs_index which is used to find the responsible hsdirs. This index
+ * value is used to select the responsible HSDir where their hsdir_index is
+ * closest to this value.
+ * SHA3-256("store-at-idx" | blinded_public_key |
+ * INT_8(replicanum) | INT_8(period_num) )
+ *
+ * hs_index_out must be large enough to receive DIGEST256_LEN bytes. */
+void
+hs_build_hs_index(uint64_t replica, const ed25519_public_key_t *blinded_pk,
+ uint64_t period_num, uint8_t *hs_index_out)
+{
+ crypto_digest_t *digest;
+
+ tor_assert(blinded_pk);
+ tor_assert(hs_index_out);
+
+ /* Build hs_index. See construction at top of function comment. */
+ digest = crypto_digest256_new(DIGEST_SHA3_256);
+ crypto_digest_add_bytes(digest, HS_INDEX_PREFIX, HS_INDEX_PREFIX_LEN);
+ crypto_digest_add_bytes(digest, (const char *) blinded_pk->pubkey,
+ ED25519_PUBKEY_LEN);
+ crypto_digest_add_bytes(digest, (const char *) &replica, sizeof(replica));
+ crypto_digest_add_bytes(digest, (const char *) &period_num,
+ sizeof(period_num));
+ crypto_digest_get_digest(digest, (char *) hs_index_out, DIGEST256_LEN);
+ crypto_digest_free(digest);
+}
+
+/* Build hsdir_index which is used to find the responsible hsdirs. This is the
+ * index value that is compare to the hs_index when selecting an HSDir.
+ * SHA3-256("node-idx" | node_identity |
+ * shared_random_value | INT_8(period_num) )
+ *
+ * hsdir_index_out must be large enough to receive DIGEST256_LEN bytes. */
+void
+hs_build_hsdir_index(const ed25519_public_key_t *identity_pk,
+ const uint8_t *srv_value, uint64_t period_num,
+ uint8_t *hsdir_index_out)
+{
+ crypto_digest_t *digest;
+
+ tor_assert(identity_pk);
+ tor_assert(srv_value);
+ tor_assert(hsdir_index_out);
+
+ /* Build hsdir_index. See construction at top of function comment. */
+ digest = crypto_digest256_new(DIGEST_SHA3_256);
+ crypto_digest_add_bytes(digest, HSDIR_INDEX_PREFIX, HSDIR_INDEX_PREFIX_LEN);
+ crypto_digest_add_bytes(digest, (const char *) identity_pk->pubkey,
+ ED25519_PUBKEY_LEN);
+ crypto_digest_add_bytes(digest, (const char *) srv_value, DIGEST256_LEN);
+ crypto_digest_add_bytes(digest, (const char *) &period_num,
+ sizeof(period_num));
+ crypto_digest_get_digest(digest, (char *) hsdir_index_out, DIGEST256_LEN);
+ crypto_digest_free(digest);
+}
+
+/* Return a newly allocated buffer containing the current shared random value
+ * or if not present, a disaster value is computed using the given time period
+ * number. This function can't fail. */
+uint8_t *
+hs_get_current_srv(uint64_t time_period_num)
+{
+ uint8_t *sr_value = tor_malloc_zero(DIGEST256_LEN);
+ const sr_srv_t *current_srv = sr_get_current();
+
+ if (current_srv) {
+ memcpy(sr_value, current_srv->value, sizeof(current_srv->value));
+ } else {
+ /* Disaster mode. */
+ get_disaster_srv(time_period_num, sr_value);
+ }
+ return sr_value;
+}
+
+/* Return a newly allocated buffer containing the previous shared random
+ * value or if not present, a disaster value is computed using the given time
+ * period number. This function can't fail. */
+uint8_t *
+hs_get_previous_srv(uint64_t time_period_num)
+{
+ uint8_t *sr_value = tor_malloc_zero(DIGEST256_LEN);
+ const sr_srv_t *previous_srv = sr_get_previous();
+
+ if (previous_srv) {
+ memcpy(sr_value, previous_srv->value, sizeof(previous_srv->value));
+ } else {
+ /* Disaster mode. */
+ get_disaster_srv(time_period_num, sr_value);
+ }
+ return sr_value;
+}
+
/* Initialize the entire HS subsytem. This is called in tor_init() before any
* torrc options are loaded. Only for >= v3. */
void