[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[gnunet] 14/40: NEWS: Added api to store hellos with peerstore service.
From: |
gnunet |
Subject: |
[gnunet] 14/40: NEWS: Added api to store hellos with peerstore service. |
Date: |
Thu, 05 Oct 2023 08:57:17 +0200 |
This is an automated email from the git hooks/post-receive script.
martin-schanzenbach pushed a commit to branch master
in repository gnunet.
commit 0f8b71280614e9a69d7703d88cc35108e6cec052
Author: t3sserakt <t3ss@posteo.de>
AuthorDate: Thu Aug 3 10:48:39 2023 +0200
NEWS: Added api to store hellos with peerstore service.
---
src/hello/hello-uri.c | 121 +++++++++++++++++
src/include/gnunet_hello_uri_lib.h | 17 +++
src/include/gnunet_peerstore_service.h | 31 +++++
src/peerstore/peerstore_api.c | 238 +++++++++++++++++++++++++++++++++
4 files changed, 407 insertions(+)
diff --git a/src/hello/hello-uri.c b/src/hello/hello-uri.c
index 8f8f699e9..9e8d6909d 100644
--- a/src/hello/hello-uri.c
+++ b/src/hello/hello-uri.c
@@ -204,6 +204,32 @@ struct GNUNET_HELLO_Builder
};
+/**
+ * Struct to wrap data to do the merge of to hello uris.
+ */
+struct AddressUriMergeResult
+{
+ /**
+ * The builder of the hello uri we merge with.
+ */
+ struct GNUNET_HELLO_Builder *builder;
+
+ /**
+ * The actual address to check, if it is allready in the hello uri we merge
with.
+ */
+ const char *address_uri;
+
+ /**
+ * Did we found the actual address to check.
+ */
+ unsigned int found;
+
+ /**
+ * Did we found at least one address to merge.
+ */
+ unsigned int merged;
+};
+
/**
* Compute @a hash over addresses in @a builder.
@@ -315,6 +341,13 @@ GNUNET_HELLO_builder_new (const struct GNUNET_PeerIdentity
*pid)
}
+struct GNUNET_PeerIdentity *
+GNUNET_HELLO_builder_get_id (struct GNUNET_HELLO_Builder *builder)
+{
+ return &builder->pid;
+}
+
+
void
GNUNET_HELLO_builder_free (struct GNUNET_HELLO_Builder *builder)
{
@@ -412,6 +445,94 @@ GNUNET_HELLO_builder_from_block (const void *block,
}
+static void
+merge_hellos2 (void *cls, const char *address_uri2)
+{
+ struct AddressUriMergeResult *aumr = cls;
+ const char *address_uri1 = aumr->address_uri;
+
+ if (GNUNET_NO == aumr->found && 0 != GNUNET_memcmp (address_uri1,
+ address_uri2))
+ {
+ aumr->found = GNUNET_YES;
+ }
+}
+
+
+static void
+merge_hellos1 (void *cls, const char *address_uri1)
+{
+ struct AddressUriMergeResult *aumr = cls;
+ struct GNUNET_HELLO_Builder *builder2 = aumr->builder;
+ struct GNUNET_PeerIdentity *peer2 = GNUNET_HELLO_builder_get_id (builder2);
+
+ aumr->address_uri = address_uri1;
+ GNUNET_HELLO_builder_iterate (builder2, peer2, &merge_hellos2, aumr);
+ if (GNUNET_YES == aumr->found)
+ {
+ GNUNET_HELLO_builder_add_address (builder2, address_uri1);
+ aumr->merged = GNUNET_YES;
+ }
+ aumr->found = GNUNET_NO;
+}
+
+
+struct GNUNET_MQ_Envelope *
+GNUNET_HELLO_builder_merge_hellos (const struct GNUNET_MessageHeader *msg1,
+ const struct GNUNET_MessageHeader *msg2,
+ const struct
+ GNUNET_CRYPTO_EddsaPrivateKey *priv)
+{
+ struct HelloUriMessage *hum1 = (struct HelloUriMessage *) msg1;
+ struct BlockHeader *bh1 = (struct BlockHeader *) &msg1[1];
+ struct GNUNET_TIME_Absolute expiration_time1 = GNUNET_TIME_absolute_ntoh (
+ bh1->expiration_time);
+ struct HelloUriMessage *hum2 = (struct HelloUriMessage *) msg2;
+ struct BlockHeader *bh2 = (struct BlockHeader *) &msg2[1];
+ struct GNUNET_TIME_Absolute expiration_time2 = GNUNET_TIME_absolute_ntoh (
+ bh1->expiration_time);
+ struct GNUNET_HELLO_Builder *builder1 = GNUNET_HELLO_builder_from_msg (msg1);
+ struct GNUNET_HELLO_Builder *builder2 = GNUNET_HELLO_builder_from_msg (msg2);
+ struct AddressUriMergeResult *aumr = GNUNET_new (struct
+ AddressUriMergeResult);
+ struct GNUNET_PeerIdentity *peer1 = GNUNET_HELLO_builder_get_id (builder1);
+ struct GNUNET_MQ_Envelope *env;
+ struct GNUNET_TIME_Absolute expiration_time;
+
+ aumr->builder = builder2;
+ GNUNET_HELLO_builder_iterate (builder1, peer1, &merge_hellos1, aumr);
+
+ if (GNUNET_YES == aumr->merged)
+ {
+ if (expiration_time1.abs_value_us < expiration_time2.abs_value_us)
+ expiration_time = expiration_time1;
+ else
+ expiration_time = expiration_time2;
+ env = GNUNET_HELLO_builder_to_env (builder2,
+ priv,
+ GNUNET_TIME_absolute_get_remaining (
+ expiration_time));
+ }
+ else if (expiration_time1.abs_value_us != expiration_time2.abs_value_us)
+ {
+ if (expiration_time1.abs_value_us < expiration_time2.abs_value_us)
+ expiration_time = expiration_time2;
+ else
+ expiration_time = expiration_time1;
+ env = GNUNET_HELLO_builder_to_env (builder2,
+ priv,
+ GNUNET_TIME_absolute_get_remaining (
+ expiration_time));
+ }
+
+ GNUNET_HELLO_builder_free (builder1);
+ GNUNET_HELLO_builder_free (builder2);
+ GNUNET_free (aumr);
+
+ return env;
+}
+
+
struct GNUNET_HELLO_Builder *
GNUNET_HELLO_builder_from_url (const char *url)
{
diff --git a/src/include/gnunet_hello_uri_lib.h
b/src/include/gnunet_hello_uri_lib.h
index 4e48bc1a0..3aa07d760 100644
--- a/src/include/gnunet_hello_uri_lib.h
+++ b/src/include/gnunet_hello_uri_lib.h
@@ -69,6 +69,13 @@ struct GNUNET_HELLO_Builder *
GNUNET_HELLO_builder_new (const struct GNUNET_PeerIdentity *pid);
+/**
+ * Get the PeerIdentity for this builder.
+ */
+struct GNUNET_PeerIdentity *
+GNUNET_HELLO_builder_get_id (struct GNUNET_HELLO_Builder *builder);
+
+
/**
* Release resources of a @a builder.
*
@@ -110,6 +117,16 @@ struct GNUNET_HELLO_Builder *
GNUNET_HELLO_builder_from_url (const char *url);
+/**
+ * Merge to hello uris.
+ */
+struct GNUNET_MQ_Envelope *
+GNUNET_HELLO_builder_merge_hellos (const struct GNUNET_MessageHeader *msg1,
+ const struct GNUNET_MessageHeader *msg2,
+ const struct
+ GNUNET_CRYPTO_EddsaPrivateKey *priv);
+
+
/**
* Generate envelope with GNUnet HELLO message (including
* peer ID) from a @a builder
diff --git a/src/include/gnunet_peerstore_service.h
b/src/include/gnunet_peerstore_service.h
index c4000c680..37d3ca7fe 100644
--- a/src/include/gnunet_peerstore_service.h
+++ b/src/include/gnunet_peerstore_service.h
@@ -46,6 +46,10 @@ extern "C" {
#endif
#endif
+/**
+ * Key used for storing HELLO in the peerstore
+ */
+#define GNUNET_PEERSTORE_HELLO_KEY "peerstore-peer-hello-uri"
/**
* Key used for storing addresses in URL format in the peerstore
@@ -182,6 +186,33 @@ typedef void (*GNUNET_PEERSTORE_Processor) (
const char *emsg);
+
+/**
+ * Add hello to peerstore.
+ *
+ * @param h handle for peerstore.
+ * @param msg The hello to add.
+ * @param cont The continuation function to execute after storing.
+ * @param cont_cls The continuation function closure.
+ * @return The context for storing.
+ */
+struct GNUNET_PEERSTORE_StoreHelloContext *
+GNUNET_PEERSTORE_hello_add (struct GNUNET_PEERSTORE_Handle *h,
+ const struct GNUNET_MessageHeader *msg,
+ const struct GNUNET_CRYPTO_EddsaPrivateKey *priv,
+ GNUNET_PEERSTORE_Continuation cont,
+ void *cont_cls);
+
+
+/**
+ * Cancel the request to add a hello.
+ *
+ * @param huc The context for storing a hello.
+ */
+void
+GNUNET_PEERSTORE_hello_add_cancel (struct GNUNET_PEERSTORE_StoreHelloContext
*huc);
+
+
/**
* Connect to the PEERSTORE service.
*
diff --git a/src/peerstore/peerstore_api.c b/src/peerstore/peerstore_api.c
index 1c13369cf..3905b14e4 100644
--- a/src/peerstore/peerstore_api.c
+++ b/src/peerstore/peerstore_api.c
@@ -25,8 +25,10 @@
*/
#include "platform.h"
#include "gnunet_util_lib.h"
+#include "gnunet_hello_uri_lib.h"
#include "peerstore.h"
#include "peerstore_common.h"
+#include "gnunet_peerstore_service.h"
#define LOG(kind, ...) GNUNET_log_from (kind, "peerstore-api", __VA_ARGS__)
@@ -156,6 +158,22 @@ struct GNUNET_PEERSTORE_StoreContext
enum GNUNET_PEERSTORE_StoreOption options;
};
+/**
+ * Closure for store callback when storing hello uris.
+ */
+struct StoreHelloCls
+{
+ /**
+ * The corresponding store context.
+ */
+ struct GNUNET_PEERSTORE_StoreContext *sc;
+
+ /**
+ * The corresponding hello uri add request.
+ */
+ struct GNUNET_PEERSTORE_StoreHelloContext *huc;
+};
+
/**
* Context for a iterate request
*/
@@ -243,6 +261,62 @@ struct GNUNET_PEERSTORE_WatchContext
struct GNUNET_HashCode keyhash;
};
+/**
+ * Context for a add hello uri request.
+ */
+struct GNUNET_PEERSTORE_StoreHelloContext
+{
+ /**
+ * Peerstore handle.
+ */
+ struct GNUNET_PEERSTORE_Handle *h;
+
+ /**
+ * Function to call with information.
+ */
+ GNUNET_PEERSTORE_Continuation cont;
+
+ /**
+ * Closure for @e callback.
+ */
+ void *cont_cls;
+
+ /**
+ * Head of active STORE requests.
+ */
+ struct GNUNET_PEERSTORE_StoreContext *sc_head;
+
+ /**
+ * Tail of active STORE requests.
+ */
+ struct GNUNET_PEERSTORE_StoreContext *sc_tail;
+
+ /**
+ * Iteration context to iterate through all the stored hellos.
+ */
+ struct GNUNET_PEERSTORE_IterateContext *ic;
+
+ /**
+ * Active watch to be notified about conflicting hello uri add requests.
+ */
+ struct GNUNET_PEERSTORE_WatchContext *wc;
+
+ /**
+ * Hello uri which was request for storing.
+ */
+ const struct GNUNET_MessageHeader *hello;
+
+ /**
+ * Key to sign merged hello.
+ */
+ const struct GNUNET_CRYPTO_EddsaPrivateKey *priv;
+
+ /**
+ * Was this request successful.
+ */
+ int success;
+};
+
/******************************************************************************/
/******************* DECLARATIONS
*********************/
/******************************************************************************/
@@ -935,4 +1009,168 @@ GNUNET_PEERSTORE_watch (struct GNUNET_PEERSTORE_Handle
*h,
}
+
+
+static void
+merge_success (void *cls, int success)
+{
+ struct StoreHelloCls *shu_cls = cls;
+ struct GNUNET_PEERSTORE_StoreHelloContext *huc = shu_cls->huc;
+ struct GNUNET_PEERSTORE_Handle *h = huc->h;
+
+ if (GNUNET_OK != success)
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
+ "Storing hello uri failed\n");
+ huc->cont (huc->cont_cls, success);
+ return;
+ }
+ GNUNET_CONTAINER_DLL_remove (huc->sc_head, huc->sc_tail, shu_cls->sc);
+ if (NULL == huc->sc_head)
+ {
+ GNUNET_PEERSTORE_watch_cancel (huc->wc);
+ huc->wc = NULL;
+ huc->cont (huc->cont_cls, GNUNET_OK);
+ huc->success = GNUNET_OK;
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "Storing hello uri succeeded!\n");
+ return;
+ }
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "Got notified during storing hello uri!\n");
+}
+
+
+static void
+store_hello (struct GNUNET_PEERSTORE_StoreHelloContext *huc,
+ const struct GNUNET_MessageHeader *hello)
+{
+ struct GNUNET_PEERSTORE_Handle *h = huc->h;
+ struct GNUNET_HELLO_Builder *builder;
+ struct GNUNET_PeerIdentity *pid;
+ struct GNUNET_PEERSTORE_StoreContext *sc;
+ struct StoreHelloCls *shu_cls = GNUNET_new (struct StoreHelloCls);
+
+ shu_cls->huc = huc;
+ builder = GNUNET_HELLO_builder_from_msg (hello);
+ pid = GNUNET_HELLO_builder_get_id (builder);
+ sc = GNUNET_PEERSTORE_store (h,
+ "peerstore",
+ pid,
+ GNUNET_PEERSTORE_HELLO_KEY,
+ hello,
+ sizeof(hello),
+ GNUNET_TIME_UNIT_FOREVER_ABS,
+ GNUNET_PEERSTORE_STOREOPTION_REPLACE,
+ merge_success,
+ shu_cls);
+ shu_cls->sc = sc;
+ GNUNET_CONTAINER_DLL_insert (huc->sc_head, huc->sc_tail, sc);
+ GNUNET_HELLO_builder_free (builder);
+}
+
+
+static void
+merge_uri (void *cls,
+ const struct GNUNET_PEERSTORE_Record *record,
+ const char *emsg)
+{
+ struct GNUNET_PEERSTORE_StoreHelloContext *huc = cls;
+ struct GNUNET_PEERSTORE_Handle *h = huc->h;
+ struct GNUNET_PEERSTORE_WatchContext *wc;
+ struct GNUNET_MessageHeader *hello;
+ const struct GNUNET_MessageHeader *merged_hello;
+ struct GNUNET_MQ_Envelope *env;
+ const char *val;
+
+ if (NULL != emsg)
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
+ "Got failure from PEERSTORE: %s\n",
+ emsg);
+ return;
+ }
+ if (NULL == record)
+ return;
+
+ if (NULL == huc->wc && GNUNET_NO == huc->success)
+ {
+ wc = GNUNET_PEERSTORE_watch (h,
+ "peerstore",
+ &record->peer,
+ GNUNET_PEERSTORE_HELLO_KEY,
+ &merge_uri,
+ huc);
+ huc->wc = wc;
+ }
+
+ if (NULL != record)
+ {
+ hello = record->value;
+ if ((0 == record->value_size) || ('\0' != val[record->value_size - 1]))
+ {
+ GNUNET_break (0);
+ return;
+ }
+
+ env = GNUNET_HELLO_builder_merge_hellos (huc->hello, hello, huc->priv);
+ merged_hello = GNUNET_MQ_env_get_msg (env);
+ if (NULL != merged_hello)
+ store_hello (huc, merged_hello);
+
+ GNUNET_free (env);
+
+ }
+ else
+ {
+ store_hello (huc, huc->hello);
+ }
+}
+
+
+struct GNUNET_PEERSTORE_StoreHelloContext *
+GNUNET_PEERSTORE_hello_add (struct GNUNET_PEERSTORE_Handle *h,
+ const struct GNUNET_MessageHeader *msg,
+ const struct GNUNET_CRYPTO_EddsaPrivateKey *priv,
+ GNUNET_PEERSTORE_Continuation cont,
+ void *cont_cls)
+{
+ struct GNUNET_HELLO_Builder *builder;
+ struct GNUNET_PEERSTORE_StoreHelloContext *huc;
+ struct GNUNET_PEERSTORE_IterateContext *ic;
+ struct GNUNET_PeerIdentity *pid;
+
+ huc = GNUNET_new (struct GNUNET_PEERSTORE_StoreHelloContext);
+ huc->h = h;
+ huc->cont = cont;
+ huc->cont_cls = cont_cls;
+ huc->hello = msg;
+ huc->priv = priv;
+
+ builder = GNUNET_HELLO_builder_from_msg (msg);
+ pid = GNUNET_HELLO_builder_get_id (builder);
+ ic = GNUNET_PEERSTORE_iterate (h,
+ "peerstore",
+ pid,
+ GNUNET_PEERSTORE_HELLO_KEY,
+ &merge_uri,
+ huc);
+ GNUNET_HELLO_builder_free (builder);
+ huc->ic = ic;
+
+ return huc;
+}
+
+void
+GNUNET_PEERSTORE_hello_add_cancel (struct GNUNET_PEERSTORE_StoreHelloContext
*huc)
+{
+ struct GNUNET_PEERSTORE_StoreContext *sc;
+
+ GNUNET_PEERSTORE_iterate_cancel (huc->ic);
+ GNUNET_PEERSTORE_watch_cancel (huc->wc);
+ while (NULL != (sc = huc->sc_head))
+ GNUNET_PEERSTORE_store_cancel (sc);
+ GNUNET_free (huc);
+}
+
/* end of peerstore_api.c */
--
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.
- [gnunet] 33/40: Merge branch 'master' into l20integration, (continued)
- [gnunet] 33/40: Merge branch 'master' into l20integration, gnunet, 2023/10/05
- [gnunet] 18/40: NEWS: The old hello design replaced by the new hello design., gnunet, 2023/10/05
- [gnunet] 39/40: Make fs and cadet build again; cadet hello handling suspicious, gnunet, 2023/10/05
- [gnunet] 25/40: Hello: Changed address and hello format to new TNG format., gnunet, 2023/10/05
- [gnunet] 38/40: Remove more traces of old transport, gnunet, 2023/10/05
- [gnunet] 31/40: BUILD: Make meson build without ats, tesbed, peerinfo, gnunet, 2023/10/05
- [gnunet] 37/40: Remove more traces of ATS, gnunet, 2023/10/05
- [gnunet] 30/40: Merge branch 'master' into l20integration, gnunet, 2023/10/05
- [gnunet] 40/40: Update to new transport binary, gnunet, 2023/10/05
- [gnunet] 10/40: TNG: Added Testcase that just runs two peers, and blocks., gnunet, 2023/10/05
- [gnunet] 14/40: NEWS: Added api to store hellos with peerstore service.,
gnunet <=
- [gnunet] 20/40: PEERSTORE: Moved code to scan and import hello file into peerstore from peerinfo., gnunet, 2023/10/05
- [gnunet] 26/40: Peerstore: Fixed bug in bootstrap code, gnunet, 2023/10/05
- [gnunet] 28/40: DHT: Fixed wrong group name, gnunet, 2023/10/05
- [gnunet] 11/40: CORE: Fixed bug that core is not calling GNUNET_TRANSPORT_core_receive_continue, gnunet, 2023/10/05
- [gnunet] 15/40: NEWS: Added api to get notified when hellos are stored with peerstore service., gnunet, 2023/10/05
- [gnunet] 08/40: TNG: Added generic start script for test cases., gnunet, 2023/10/05
- [gnunet] 21/40: NEWS: Moved code to testing to have more generic test setup, which can be used not only from within transport., gnunet, 2023/10/05
- [gnunet] 23/40: NEWS: Changed method GNUNET_HELLO_builder_get_expiration_time to not need parameter GNUNET_HELLO_Builder., gnunet, 2023/10/05
- [gnunet] 24/40: Peerstore: Changed the behavior of GNUNET_PEERSTORE_watch to also return the values allready stored for the key., gnunet, 2023/10/05
- [gnunet] 27/40: TNG: Fixed validation bug., gnunet, 2023/10/05