From d4790594a33a4688641f66841f05533b3c0956b9 Mon Sep 17 00:00:00 2001 From: Andreas Ebner Date: Sun, 25 Aug 2019 12:23:33 +0200 Subject: Introduction of intermediate result reporting, removed some stuff, new test: - new message, message type and api function to handle intermediate result reporting - removed GNUNET_SIGNATURE_PURPOSE_CREDENTIAL completely and the one usage that was still around - new test: AND with both parts having a bidirectional forward match --- src/credential/credential.h | 18 ++++++ src/credential/credential_api.c | 68 ++++++++++++++++++++- src/credential/credential_serialization.c | 2 +- src/credential/delegate_misc.c | 4 -- src/credential/gnunet-credential.c | 19 +++++- src/credential/gnunet-service-credential.c | 49 ++++++++++++++- src/credential/test_credential_bi_and3.sh | 97 ++++++++++++++++++++++++++++++ src/include/gnunet_credential_service.h | 13 +++- src/include/gnunet_protocols.h | 2 + src/include/gnunet_signatures.h | 6 +- 10 files changed, 260 insertions(+), 18 deletions(-) create mode 100755 src/credential/test_credential_bi_and3.sh (limited to 'src') diff --git a/src/credential/credential.h b/src/credential/credential.h index 43ecec73f..504c7b464 100644 --- a/src/credential/credential.h +++ b/src/credential/credential.h @@ -145,6 +145,24 @@ struct DelegationChainResultMessage /* followed by ad_count GNUNET_CREDENTIAL_RecordData structs*/ }; +/** + * Message from CREDENTIAL service to client: new results. + */ +struct DelegationChainIntermediateMessage +{ + /** + * Header of type #GNUNET_MESSAGE_TYPE_CREDENTIAL_INTERMEDIATE_RESULT + */ + struct GNUNET_MessageHeader header; + + /** + * Unique identifier for this request (for key collisions). + */ + uint32_t id GNUNET_PACKED; + + uint32_t size GNUNET_PACKED; +}; + struct DelegationRecordData { /** diff --git a/src/credential/credential_api.c b/src/credential/credential_api.c index 7c3b35464..dd66c8c72 100644 --- a/src/credential/credential_api.c +++ b/src/credential/credential_api.c @@ -68,6 +68,16 @@ struct GNUNET_CREDENTIAL_Request */ void *proc_cls; + /** + * processor to call on intermediate result + */ + GNUNET_CREDENTIAL_IntermediateResultProcessor int_proc; + + /** + * @e verify_proc2 closure + */ + void *proc2_cls; + /** * Envelope with the message for this queue entry. */ @@ -247,6 +257,48 @@ handle_result (void *cls, const struct DelegationChainResultMessage *vr_msg) } } +static int +check_intermediate (void *cls, const struct DelegationChainIntermediateMessage *vr_msg) +{ + //TODO + return GNUNET_OK; +} + +static void +handle_intermediate (void *cls, const struct DelegationChainIntermediateMessage *vr_msg) +{ + struct GNUNET_CREDENTIAL_Handle *handle = cls; + uint32_t r_id = ntohl (vr_msg->id); + uint32_t size = ntohl (vr_msg->size); + struct GNUNET_CREDENTIAL_Request *vr; + GNUNET_CREDENTIAL_IntermediateResultProcessor proc; + void *proc_cls; + struct GNUNET_CREDENTIAL_Delegation *dd; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received intermediate reply from CREDENTIAL service\n"); + for (vr = handle->request_head; NULL != vr; vr = vr->next) + if (vr->r_id == r_id) + break; + if (NULL == vr) + return; + + proc = vr->int_proc; + proc_cls = vr->proc2_cls; + + dd = GNUNET_new (struct GNUNET_CREDENTIAL_Delegation); + GNUNET_assert ( + GNUNET_OK == + GNUNET_CREDENTIAL_delegation_chain_deserialize (size, + (const char *) &vr_msg[1], + 1, + dd, + 0, + NULL)); + + proc (proc_cls, dd); +} + + /** * Reconnect to CREDENTIAL service. @@ -265,6 +317,10 @@ reconnect (struct GNUNET_CREDENTIAL_Handle *handle) GNUNET_MESSAGE_TYPE_CREDENTIAL_COLLECT_RESULT, struct DelegationChainResultMessage, handle), + GNUNET_MQ_hd_var_size (intermediate, + GNUNET_MESSAGE_TYPE_CREDENTIAL_INTERMEDIATE_RESULT, + struct DelegationChainIntermediateMessage, + handle), GNUNET_MQ_handler_end ()}; struct GNUNET_CREDENTIAL_Request *vr; @@ -365,7 +421,9 @@ GNUNET_CREDENTIAL_collect ( const struct GNUNET_CRYPTO_EcdsaPrivateKey *subject_key, enum GNUNET_CREDENTIAL_AlgoDirectionFlags direction, GNUNET_CREDENTIAL_CredentialResultProcessor proc, - void *proc_cls) + void *proc_cls, + GNUNET_CREDENTIAL_IntermediateResultProcessor proc2, + void *proc2_cls) { /* IPC to shorten credential names, return shorten_handle */ struct CollectMessage *c_msg; @@ -392,6 +450,8 @@ GNUNET_CREDENTIAL_collect ( vr->credential_handle = handle; vr->verify_proc = proc; vr->proc_cls = proc_cls; + vr->int_proc = proc2; + vr->proc2_cls = proc2_cls; vr->r_id = handle->r_id_gen++; vr->env = GNUNET_MQ_msg_extra (c_msg, nlen, GNUNET_MESSAGE_TYPE_CREDENTIAL_COLLECT); @@ -435,7 +495,9 @@ GNUNET_CREDENTIAL_verify ( const struct GNUNET_CREDENTIAL_Delegate *delegates, enum GNUNET_CREDENTIAL_AlgoDirectionFlags direction, GNUNET_CREDENTIAL_CredentialResultProcessor proc, - void *proc_cls) + void *proc_cls, + GNUNET_CREDENTIAL_IntermediateResultProcessor proc2, + void *proc2_cls) { /* IPC to shorten credential names, return shorten_handle */ struct VerifyMessage *v_msg; @@ -465,6 +527,8 @@ GNUNET_CREDENTIAL_verify ( vr->credential_handle = handle; vr->verify_proc = proc; vr->proc_cls = proc_cls; + vr->int_proc = proc2; + vr->proc2_cls = proc2_cls; vr->r_id = handle->r_id_gen++; vr->env = GNUNET_MQ_msg_extra (v_msg, nlen, GNUNET_MESSAGE_TYPE_CREDENTIAL_VERIFY); diff --git a/src/credential/credential_serialization.c b/src/credential/credential_serialization.c index 240ab4dca..28773de8e 100644 --- a/src/credential/credential_serialization.c +++ b/src/credential/credential_serialization.c @@ -191,7 +191,7 @@ GNUNET_CREDENTIAL_delegates_serialize ( c_rec.issuer_key = cd[i].issuer_key; c_rec.subject_key = cd[i].subject_key; c_rec.signature = cd[i].signature; - c_rec.purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_CREDENTIAL); + c_rec.purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_DELEGATE); c_rec.purpose.size = htonl ((sizeof (struct DelegateEntry) + cd[i].issuer_attribute_len) - sizeof (struct GNUNET_CRYPTO_EcdsaSignature)); diff --git a/src/credential/delegate_misc.c b/src/credential/delegate_misc.c index e29859e8c..25356ef7f 100644 --- a/src/credential/delegate_misc.c +++ b/src/credential/delegate_misc.c @@ -271,8 +271,4 @@ GNUNET_CREDENTIAL_delegate_issue ( GNUNET_free (del); return dele; - - // Entweder: strdup und destroy (free auf die subjct_attribute/issuer_attribute) - // oder: pointer auf cred[1], aber nach jedem string im combined string ein EOS <- besser - // function comment: cred must be freed by caller, (add missing sub_iss) } diff --git a/src/credential/gnunet-credential.c b/src/credential/gnunet-credential.c index f2d967eea..aa9828d4b 100644 --- a/src/credential/gnunet-credential.c +++ b/src/credential/gnunet-credential.c @@ -263,6 +263,17 @@ do_timeout (void *cls) GNUNET_SCHEDULER_shutdown (); } +static void +handle_intermediate_result(void *cls, +struct GNUNET_CREDENTIAL_Delegation *dd) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Intermediate result: %s.%s <- %s.%s\n", + GNUNET_CRYPTO_ecdsa_public_key_to_string (&dd->issuer_key), + dd->issuer_attribute, + GNUNET_CRYPTO_ecdsa_public_key_to_string (&dd->subject_key), + dd->subject_attribute); +} + static void handle_collect_result (void *cls, unsigned int d_count, @@ -395,7 +406,9 @@ identity_cb (void *cls, const struct GNUNET_IDENTITY_Ego *ego) privkey, direction, &handle_collect_result, - NULL); + NULL, + &handle_intermediate_result, + NULL); return; } GNUNET_SCHEDULER_shutdown (); @@ -901,7 +914,9 @@ run (void *cls, delegates, direction, &handle_verify_result, - NULL); + NULL, + &handle_intermediate_result, + NULL); for (i = 0; i < count; i++) { GNUNET_free ((char *) delegates[i].issuer_attribute); diff --git a/src/credential/gnunet-service-credential.c b/src/credential/gnunet-service-credential.c index 90316f203..cb0dca6b8 100644 --- a/src/credential/gnunet-service-credential.c +++ b/src/credential/gnunet-service-credential.c @@ -246,7 +246,6 @@ struct DelegationSetQueueEntry */ struct VerifyRequestHandle { - /** * We keep these in a DLL. */ @@ -480,6 +479,48 @@ shutdown_task (void *cls) } } +static void +send_intermediate_response(struct VerifyRequestHandle *vrh, struct DelegationChainEntry *ch_entry){ + struct DelegationChainIntermediateMessage *rmsg; + struct GNUNET_MQ_Envelope *env; + struct GNUNET_CREDENTIAL_Delegation *dd; + size_t size; + + dd = GNUNET_new (struct GNUNET_CREDENTIAL_Delegation); + dd->issuer_key = ch_entry->issuer_key; + dd->subject_key = ch_entry->subject_key; + dd->issuer_attribute = ch_entry->issuer_attribute; + dd->issuer_attribute_len = strlen (ch_entry->issuer_attribute) + 1; + dd->subject_attribute_len = 0; + dd->subject_attribute = NULL; + if (NULL != ch_entry->subject_attribute) + { + dd->subject_attribute = ch_entry->subject_attribute; + dd->subject_attribute_len = strlen (ch_entry->subject_attribute) + 1; + } + + + size = GNUNET_CREDENTIAL_delegation_chain_get_size (1, + dd, + 0, + NULL); + + env = GNUNET_MQ_msg_extra (rmsg, + size, + GNUNET_MESSAGE_TYPE_CREDENTIAL_INTERMEDIATE_RESULT); + // Assign id so that client can find associated request + rmsg->id = vrh->request_id; + rmsg->size = htonl(size); + + GNUNET_assert ( + -1 != GNUNET_CREDENTIAL_delegation_chain_serialize (1, + dd, + 0, + NULL, + size, + (char *) &rmsg[1])); + GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (vrh->client), env); +} static void send_lookup_response (struct VerifyRequestHandle *vrh) @@ -821,6 +862,9 @@ forward_resolution (void *cls, ds_entry->delegation_chain_entry->issuer_key = del->issuer_key; ds_entry->delegation_chain_entry->issuer_attribute = GNUNET_strdup (del->issuer_attribute); + + // Found new entry, repoting intermediate result + send_intermediate_response(vrh, ds_entry->delegation_chain_entry); // current delegation as parent ds_entry->parent_queue_entry = dq_entry; @@ -1035,6 +1079,9 @@ backward_resolution (void *cls, ds_entry->delegation_chain_entry->issuer_attribute = GNUNET_strdup (current_set->lookup_attribute); + // Found new entry, repoting intermediate result + send_intermediate_response(vrh, ds_entry->delegation_chain_entry); + ds_entry->parent_queue_entry = dq_entry; // current_delegation; /** diff --git a/src/credential/test_credential_bi_and3.sh b/src/credential/test_credential_bi_and3.sh new file mode 100755 index 000000000..83f2374a5 --- /dev/null +++ b/src/credential/test_credential_bi_and3.sh @@ -0,0 +1,97 @@ +#!/usr/bin/env bash +trap "gnunet-arm -e -c test_credential_lookup.conf" SIGINT + +LOCATION=$(which gnunet-config) +if [ -z $LOCATION ] +then + LOCATION="gnunet-config" +fi +$LOCATION --version 1> /dev/null +if test $? != 0 +then + echo "GNUnet command line tools cannot be found, check environmental variables PATH and GNUNET_PREFIX" + exit 77 +fi + +rm -rf `gnunet-config -c test_credential_lookup.conf -s PATHS -o GNUNET_HOME -f` + + + + +which timeout > /dev/null 2>&1 && DO_TIMEOUT="timeout 10" +gnunet-arm -s -c test_credential_lookup.conf + +gnunet-identity -C a -c test_credential_lookup.conf +gnunet-identity -C b -c test_credential_lookup.conf +gnunet-identity -C c -c test_credential_lookup.conf +gnunet-identity -C d -c test_credential_lookup.conf +gnunet-identity -C e -c test_credential_lookup.conf +gnunet-identity -C f -c test_credential_lookup.conf +gnunet-identity -C g -c test_credential_lookup.conf +gnunet-identity -C h -c test_credential_lookup.conf +AKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep a | awk '{print $3}') +BKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep b | awk '{print $3}') +CKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep c | awk '{print $3}') +DKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep d | awk '{print $3}') +EKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep e | awk '{print $3}') +FKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep f | awk '{print $3}') +GKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep g | awk '{print $3}') +HKEY=$(gnunet-identity -d -c test_credential_lookup.conf | grep h | awk '{print $3}') + +# (1) (A.a) <- B.b +# (2) (B.b) <- C.c AND G.g +# (3) C.c <- (D.d) +# (4) D.d <- (E.e) +# (5) E.e <- (F) priv +# (6) G.g <- (H.h) +# (7) H.h <- (F) priv + +# BIDIRECTIONAL +gnunet-credential --createIssuerSide --ego=a --attribute="a" --subject="$BKEY b" --ttl=5m -c test_credential_lookup.conf +gnunet-namestore -D -z a +gnunet-credential --createIssuerSide --ego=b --attribute="b" --subject="$CKEY c, $GKEY g" --ttl=5m -c test_credential_lookup.conf +gnunet-namestore -D -z b + +SIGNED=`$DO_TIMEOUT gnunet-credential --signSubjectSide --ego=c --attribute="c" --subject="$DKEY d" --ttl="2019-12-12 10:00:00"` +gnunet-credential --createSubjectSide --ego=d --import "$SIGNED" +gnunet-namestore -D -z d +SIGNED=`$DO_TIMEOUT gnunet-credential --signSubjectSide --ego=d --attribute="d" --subject="$EKEY e" --ttl="2019-12-12 10:00:00"` +gnunet-credential --createSubjectSide --ego=e --import "$SIGNED" +gnunet-namestore -D -z e +SIGNED=`$DO_TIMEOUT gnunet-credential --signSubjectSide --ego=g --attribute="g" --subject="$HKEY h" --ttl="2019-12-12 10:00:00"` +gnunet-credential --createSubjectSide --ego=h --import "$SIGNED" +gnunet-namestore -D -z h +SIGNED=`$DO_TIMEOUT gnunet-credential --signSubjectSide --ego=e --attribute="e" --subject="$FKEY" --ttl="2019-12-12 10:00:00"` +gnunet-credential --createSubjectSide --ego=f --import "$SIGNED" --private +SIGNED=`$DO_TIMEOUT gnunet-credential --signSubjectSide --ego=h --attribute="h" --subject="$FKEY" --ttl="2019-12-12 10:00:00"` +gnunet-credential --createSubjectSide --ego=f --import "$SIGNED" --private +gnunet-namestore -D -z f + +# Starting to resolve +echo "+++ Starting to Resolve +++" + +DELS=`$DO_TIMEOUT gnunet-credential --collect --issuer=$AKEY --attribute="a" --ego=f -c test_credential_lookup.conf | paste -d, -s - -` +echo $DELS +echo gnunet-credential --verify --issuer=$AKEY --attribute="a" --subject=$FKEY --delegate=\'$DELS\' -c test_credential_lookup.conf +RES_DELS=`gnunet-credential --verify --issuer=$AKEY --attribute="a" --subject=$FKEY --delegate="$DELS" -c test_credential_lookup.conf` + +# Cleanup properly +gnunet-namestore -z a -d -n "a" -t ATTR -c test_credential_lookup.conf +gnunet-namestore -z b -d -n "b" -t ATTR -c test_credential_lookup.conf +gnunet-namestore -z d -d -n "@" -t DEL -c test_credential_lookup.conf +gnunet-namestore -z e -d -n "@" -t DEL -c test_credential_lookup.conf +gnunet-namestore -z f -d -n "@" -t DEL -c test_credential_lookup.conf +gnunet-namestore -z h -d -n "@" -t DEL -c test_credential_lookup.conf + +gnunet-arm -e -c test_credential_lookup.conf + +if [ "$RES_DELS" != "Failed." ] +then + # TODO: replace echo -e bashism + echo -e "${RES_DELS}" + exit 0 +else + echo "FAIL: Failed to verify credential $RES_DELS." + exit 1 +fi + diff --git a/src/include/gnunet_credential_service.h b/src/include/gnunet_credential_service.h index be682c3b5..fdee3b641 100644 --- a/src/include/gnunet_credential_service.h +++ b/src/include/gnunet_credential_service.h @@ -259,7 +259,10 @@ typedef void (*GNUNET_CREDENTIAL_CredentialResultProcessor) (void *cls, unsigned int d_count, struct GNUNET_CREDENTIAL_Delegation *delegation_chain, unsigned int c_count, - struct GNUNET_CREDENTIAL_Delegate *credential); + struct GNUNET_CREDENTIAL_Delegate *delegte); + +typedef void (*GNUNET_CREDENTIAL_IntermediateResultProcessor) (void *cls, + struct GNUNET_CREDENTIAL_Delegation *delegation); /** * Iterator called on obtained result for an attribute delegation. @@ -309,7 +312,9 @@ GNUNET_CREDENTIAL_verify (struct GNUNET_CREDENTIAL_Handle *handle, const struct GNUNET_CREDENTIAL_Delegate *delegates, enum GNUNET_CREDENTIAL_AlgoDirectionFlags direction, GNUNET_CREDENTIAL_CredentialResultProcessor proc, - void *proc_cls); + void *proc_cls, + GNUNET_CREDENTIAL_IntermediateResultProcessor, + void *proc2_cls); struct GNUNET_CREDENTIAL_Request* GNUNET_CREDENTIAL_collect (struct GNUNET_CREDENTIAL_Handle *handle, @@ -318,7 +323,9 @@ GNUNET_CREDENTIAL_collect (struct GNUNET_CREDENTIAL_Handle *handle, const struct GNUNET_CRYPTO_EcdsaPrivateKey *subject_key, enum GNUNET_CREDENTIAL_AlgoDirectionFlags direction, GNUNET_CREDENTIAL_CredentialResultProcessor proc, - void *proc_cls); + void *proc_cls, + GNUNET_CREDENTIAL_IntermediateResultProcessor, + void *proc2_cls); /** * Delegate an attribute diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h index c932c44d0..4ca1ad47a 100644 --- a/src/include/gnunet_protocols.h +++ b/src/include/gnunet_protocols.h @@ -2726,6 +2726,8 @@ extern "C" { #define GNUNET_MESSAGE_TYPE_CREDENTIAL_COLLECT_RESULT 984 +#define GNUNET_MESSAGE_TYPE_CREDENTIAL_INTERMEDIATE_RESULT 985 + /******************************************************************************/ diff --git a/src/include/gnunet_signatures.h b/src/include/gnunet_signatures.h index 1d6d5a229..a00e0372d 100644 --- a/src/include/gnunet_signatures.h +++ b/src/include/gnunet_signatures.h @@ -188,7 +188,7 @@ extern "C" /** * Signature for a GNUnet credential */ -#define GNUNET_SIGNATURE_PURPOSE_CREDENTIAL 28 +#define GNUNET_SIGNATURE_PURPOSE_DELEGATE 28 /** * Signature by a peer affirming that this is one of its @@ -241,10 +241,6 @@ extern "C" */ #define GNUNET_SIGNATURE_PURPOSE_TRANSPORT_DV_INITIATOR 37 -/** - * Signature for a GNUnet delegate - */ -#define GNUNET_SIGNATURE_PURPOSE_DELEGATE 38 #if 0 /* keep Emacsens' auto-indent happy */ { -- cgit v1.2.3