2 This file is part of GNUnet.
3 Copyright (C) 2016 GNUnet e.V.
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public Liceidentity as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public Liceidentity for more details.
15 You should have received a copy of the GNU General Public Liceidentity
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 Boston, MA 02110-1301, USA.
22 * @file identity-provider/identity_provider_api.c
23 * @brief api to interact with the identity provider service
24 * @author Martin Schanzenbach
27 #include "gnunet_util_lib.h"
28 #include "gnunet_constants.h"
29 #include "gnunet_protocols.h"
30 #include "gnunet_mq_lib.h"
31 #include "gnunet_identity_provider_service.h"
32 #include "gnunet_identity_attribute_lib.h"
33 #include "identity_provider.h"
35 #define LOG(kind,...) GNUNET_log_from (kind, "identity-api",__VA_ARGS__)
39 * Handle for an operation with the service.
41 struct GNUNET_IDENTITY_PROVIDER_Operation
47 struct GNUNET_IDENTITY_PROVIDER_Handle *h;
50 * We keep operations in a DLL.
52 struct GNUNET_IDENTITY_PROVIDER_Operation *next;
55 * We keep operations in a DLL.
57 struct GNUNET_IDENTITY_PROVIDER_Operation *prev;
60 * Message to send to the service.
61 * Allocated at the end of this struct.
63 const struct GNUNET_MessageHeader *msg;
66 * Continuation to invoke after attribute store call
68 GNUNET_IDENTITY_PROVIDER_ContinuationWithStatus as_cb;
71 * Attribute result callback
73 GNUNET_IDENTITY_PROVIDER_AttributeResult ar_cb;
76 * Revocation result callback
78 GNUNET_IDENTITY_PROVIDER_ContinuationWithStatus rvk_cb;
81 * Ticket result callback
83 GNUNET_IDENTITY_PROVIDER_TicketCallback tr_cb;
86 * Envelope with the message for this queue entry.
88 struct GNUNET_MQ_Envelope *env;
96 * Closure for @e cont or @e cb.
103 * Handle for a ticket iterator operation
105 struct GNUNET_IDENTITY_PROVIDER_TicketIterator
111 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *next;
116 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *prev;
119 * Main handle to access the idp.
121 struct GNUNET_IDENTITY_PROVIDER_Handle *h;
124 * Function to call on completion.
126 GNUNET_SCHEDULER_TaskCallback finish_cb;
129 * Closure for @e error_cb.
134 * The continuation to call with the results
136 GNUNET_IDENTITY_PROVIDER_TicketCallback tr_cb;
139 * Closure for @e tr_cb.
144 * Function to call on errors.
146 GNUNET_SCHEDULER_TaskCallback error_cb;
149 * Closure for @e error_cb.
154 * Envelope of the message to send to the service, if not yet
157 struct GNUNET_MQ_Envelope *env;
160 * The operation id this zone iteration operation has
168 * Handle for a attribute iterator operation
170 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator
176 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *next;
181 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *prev;
184 * Main handle to access the idp.
186 struct GNUNET_IDENTITY_PROVIDER_Handle *h;
189 * Function to call on completion.
191 GNUNET_SCHEDULER_TaskCallback finish_cb;
194 * Closure for @e error_cb.
199 * The continuation to call with the results
201 GNUNET_IDENTITY_PROVIDER_AttributeResult proc;
204 * Closure for @e proc.
209 * Function to call on errors.
211 GNUNET_SCHEDULER_TaskCallback error_cb;
214 * Closure for @e error_cb.
219 * Envelope of the message to send to the service, if not yet
222 struct GNUNET_MQ_Envelope *env;
225 * Private key of the zone.
227 struct GNUNET_CRYPTO_EcdsaPrivateKey identity;
230 * The operation id this zone iteration operation has
238 * Handle for the service.
240 struct GNUNET_IDENTITY_PROVIDER_Handle
243 * Configuration to use.
245 const struct GNUNET_CONFIGURATION_Handle *cfg;
248 * Socket (if available).
250 struct GNUNET_CLIENT_Connection *client;
258 * Head of active operations.
260 struct GNUNET_IDENTITY_PROVIDER_Operation *op_head;
263 * Tail of active operations.
265 struct GNUNET_IDENTITY_PROVIDER_Operation *op_tail;
268 * Head of active iterations
270 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it_head;
273 * Tail of active iterations
275 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it_tail;
278 * Head of active iterations
280 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *ticket_it_head;
283 * Tail of active iterations
285 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *ticket_it_tail;
289 * Currently pending transmission request, or NULL for none.
291 struct GNUNET_CLIENT_TransmitHandle *th;
294 * Task doing exponential back-off trying to reconnect.
296 struct GNUNET_SCHEDULER_Task * reconnect_task;
299 * Time for next connect retry.
301 struct GNUNET_TIME_Relative reconnect_backoff;
304 * Connection to service (if available).
306 struct GNUNET_MQ_Handle *mq;
309 * Request Id generator. Incremented by one for each request.
314 * Are we polling for incoming messages right now?
321 * Try again to connect to the service.
323 * @param h handle to the identity provider service.
326 reconnect (struct GNUNET_IDENTITY_PROVIDER_Handle *h);
331 * @param cls the handle
334 reconnect_task (void *cls)
336 struct GNUNET_IDENTITY_PROVIDER_Handle *handle = cls;
338 handle->reconnect_task = NULL;
344 * Disconnect from service and then reconnect.
346 * @param handle our service
349 force_reconnect (struct GNUNET_IDENTITY_PROVIDER_Handle *handle)
351 GNUNET_MQ_destroy (handle->mq);
353 handle->reconnect_backoff
354 = GNUNET_TIME_STD_BACKOFF (handle->reconnect_backoff);
355 handle->reconnect_task
356 = GNUNET_SCHEDULER_add_delayed (handle->reconnect_backoff,
364 * @param it entry to free
367 free_it (struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it)
369 struct GNUNET_IDENTITY_PROVIDER_Handle *h = it->h;
371 GNUNET_CONTAINER_DLL_remove (h->it_head,
375 GNUNET_MQ_discard (it->env);
380 free_op (struct GNUNET_IDENTITY_PROVIDER_Operation* op)
385 GNUNET_MQ_discard (op->env);
391 * Generic error handler, called with the appropriate error code and
392 * the same closure specified at the creation of the message queue.
393 * Not every message queue implementation supports an error handler.
395 * @param cls closure with the `struct GNUNET_GNS_Handle *`
396 * @param error error code
399 mq_error_handler (void *cls,
400 enum GNUNET_MQ_Error error)
402 struct GNUNET_IDENTITY_PROVIDER_Handle *handle = cls;
403 force_reconnect (handle);
407 * Handle an incoming message of type
408 * #GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE_RESPONSE
411 * @param msg the message we received
414 handle_attribute_store_response (void *cls,
415 const struct AttributeStoreResultMessage *msg)
417 struct GNUNET_IDENTITY_PROVIDER_Handle *h = cls;
418 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
419 uint32_t r_id = ntohl (msg->id);
423 for (op = h->op_head; NULL != op; op = op->next)
424 if (op->r_id == r_id)
429 res = ntohl (msg->op_result);
430 LOG (GNUNET_ERROR_TYPE_DEBUG,
431 "Received ATTRIBUTE_STORE_RESPONSE with result %d\n",
434 /* TODO: add actual error message to response... */
435 if (GNUNET_SYSERR == res)
436 emsg = _("failed to store record\n");
439 if (NULL != op->as_cb)
443 GNUNET_CONTAINER_DLL_remove (h->op_head,
452 * Handle an incoming message of type
453 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_CONSUME_TICKET_RESULT
456 * @param msg the message we received
457 * @return #GNUNET_OK on success, #GNUNET_SYSERR on error
460 check_consume_ticket_result (void *cls,
461 const struct ConsumeTicketResultMessage *msg)
466 msg_len = ntohs (msg->header.size);
467 attrs_len = ntohs (msg->attrs_len);
468 if (msg_len != sizeof (struct ConsumeTicketResultMessage) + attrs_len)
471 return GNUNET_SYSERR;
478 * Handle an incoming message of type
479 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_CONSUME_TICKET_RESULT
482 * @param msg the message we received
485 handle_consume_ticket_result (void *cls,
486 const struct ConsumeTicketResultMessage *msg)
488 struct GNUNET_IDENTITY_PROVIDER_Handle *h = cls;
489 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
491 uint32_t r_id = ntohl (msg->id);
493 attrs_len = ntohs (msg->attrs_len);
494 LOG (GNUNET_ERROR_TYPE_DEBUG,
495 "Processing attribute result.\n");
498 for (op = h->op_head; NULL != op; op = op->next)
499 if (op->r_id == r_id)
505 struct GNUNET_IDENTITY_ATTRIBUTE_ClaimList *attrs;
506 struct GNUNET_IDENTITY_ATTRIBUTE_ClaimListEntry *le;
507 attrs = GNUNET_IDENTITY_ATTRIBUTE_list_deserialize ((char*)&msg[1],
509 if (NULL != op->ar_cb)
519 for (le = attrs->list_head; NULL != le; le = le->next)
523 GNUNET_IDENTITY_ATTRIBUTE_list_destroy (attrs);
531 GNUNET_CONTAINER_DLL_remove (h->op_head,
543 * Handle an incoming message of type
544 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_RESULT
547 * @param msg the message we received
548 * @return #GNUNET_OK on success, #GNUNET_SYSERR on error
551 check_attribute_result (void *cls,
552 const struct AttributeResultMessage *msg)
557 msg_len = ntohs (msg->header.size);
558 attr_len = ntohs (msg->attr_len);
559 if (msg_len != sizeof (struct AttributeResultMessage) + attr_len)
562 return GNUNET_SYSERR;
569 * Handle an incoming message of type
570 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_RESULT
573 * @param msg the message we received
576 handle_attribute_result (void *cls,
577 const struct AttributeResultMessage *msg)
579 static struct GNUNET_CRYPTO_EcdsaPrivateKey identity_dummy;
580 struct GNUNET_IDENTITY_PROVIDER_Handle *h = cls;
581 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it;
582 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
584 uint32_t r_id = ntohl (msg->id);
586 attr_len = ntohs (msg->attr_len);
587 LOG (GNUNET_ERROR_TYPE_DEBUG,
588 "Processing attribute result.\n");
591 for (it = h->it_head; NULL != it; it = it->next)
592 if (it->r_id == r_id)
594 for (op = h->op_head; NULL != op; op = op->next)
595 if (op->r_id == r_id)
597 if ((NULL == it) && (NULL == op))
600 if ( (0 == (memcmp (&msg->identity,
602 sizeof (identity_dummy)))) )
604 if ((NULL == it) && (NULL == op))
612 if (NULL != it->finish_cb)
613 it->finish_cb (it->finish_cb_cls);
618 if (NULL != op->ar_cb)
622 GNUNET_CONTAINER_DLL_remove (h->op_head,
632 struct GNUNET_IDENTITY_ATTRIBUTE_Claim *attr;
633 attr = GNUNET_IDENTITY_ATTRIBUTE_deserialize ((char*)&msg[1],
637 if (NULL != it->proc)
638 it->proc (it->proc_cls,
641 } else if (NULL != op)
643 if (NULL != op->ar_cb)
656 * Handle an incoming message of type
657 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_RESULT
660 * @param msg the message we received
661 * @return #GNUNET_OK on success, #GNUNET_SYSERR on error
664 check_ticket_result (void *cls,
665 const struct TicketResultMessage *msg)
669 msg_len = ntohs (msg->header.size);
670 if (msg_len < sizeof (struct TicketResultMessage))
673 return GNUNET_SYSERR;
681 * Handle an incoming message of type
682 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_RESULT
685 * @param msg the message we received
688 handle_ticket_result (void *cls,
689 const struct TicketResultMessage *msg)
691 struct GNUNET_IDENTITY_PROVIDER_Handle *handle = cls;
692 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
693 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *it;
694 const struct GNUNET_IDENTITY_PROVIDER_Ticket *ticket;
695 uint32_t r_id = ntohl (msg->id);
698 for (op = handle->op_head; NULL != op; op = op->next)
699 if (op->r_id == r_id)
701 for (it = handle->ticket_it_head; NULL != it; it = it->next)
702 if (it->r_id == r_id)
704 if ((NULL == op) && (NULL == it))
706 msg_len = ntohs (msg->header.size);
709 GNUNET_CONTAINER_DLL_remove (handle->op_head,
712 if (msg_len == sizeof (struct TicketResultMessage))
714 if (NULL != op->tr_cb)
715 op->tr_cb (op->cls, NULL);
717 ticket = (struct GNUNET_IDENTITY_PROVIDER_Ticket *)&msg[1];
718 if (NULL != op->tr_cb)
719 op->tr_cb (op->cls, ticket);
723 } else if (NULL != it) {
724 if (msg_len == sizeof (struct TicketResultMessage))
726 if (NULL != it->tr_cb)
727 GNUNET_CONTAINER_DLL_remove (handle->ticket_it_head,
728 handle->ticket_it_tail,
730 it->finish_cb (it->finish_cb_cls);
733 ticket = (struct GNUNET_IDENTITY_PROVIDER_Ticket *)&msg[1];
734 if (NULL != it->tr_cb)
735 it->tr_cb (it->cls, ticket);
744 * Handle an incoming message of type
745 * #GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_REVOKE_TICKET_RESULT
748 * @param msg the message we received
751 handle_revoke_ticket_result (void *cls,
752 const struct RevokeTicketResultMessage *msg)
754 struct GNUNET_IDENTITY_PROVIDER_Handle *h = cls;
755 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
756 uint32_t r_id = ntohl (msg->id);
759 LOG (GNUNET_ERROR_TYPE_DEBUG,
760 "Processing revocation result.\n");
763 for (op = h->op_head; NULL != op; op = op->next)
764 if (op->r_id == r_id)
768 success = ntohl (msg->success);
770 if (NULL != op->rvk_cb)
776 GNUNET_CONTAINER_DLL_remove (h->op_head,
788 * Try again to connect to the service.
790 * @param h handle to the identity provider service.
793 reconnect (struct GNUNET_IDENTITY_PROVIDER_Handle *h)
795 struct GNUNET_MQ_MessageHandler handlers[] = {
796 GNUNET_MQ_hd_fixed_size (attribute_store_response,
797 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_STORE_RESPONSE,
798 struct AttributeStoreResultMessage,
800 GNUNET_MQ_hd_var_size (attribute_result,
801 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_RESULT,
802 struct AttributeResultMessage,
804 GNUNET_MQ_hd_var_size (ticket_result,
805 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_RESULT,
806 struct TicketResultMessage,
808 GNUNET_MQ_hd_var_size (consume_ticket_result,
809 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_CONSUME_TICKET_RESULT,
810 struct ConsumeTicketResultMessage,
812 GNUNET_MQ_hd_fixed_size (revoke_ticket_result,
813 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_REVOKE_TICKET_RESULT,
814 struct RevokeTicketResultMessage,
816 GNUNET_MQ_handler_end ()
818 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
820 GNUNET_assert (NULL == h->mq);
821 LOG (GNUNET_ERROR_TYPE_DEBUG,
822 "Connecting to identity provider service.\n");
824 h->mq = GNUNET_CLIENT_connect (h->cfg,
831 for (op = h->op_head; NULL != op; op = op->next)
832 GNUNET_MQ_send_copy (h->mq,
838 * Connect to the identity provider service.
840 * @param cfg the configuration to use
841 * @return handle to use
843 struct GNUNET_IDENTITY_PROVIDER_Handle *
844 GNUNET_IDENTITY_PROVIDER_connect (const struct GNUNET_CONFIGURATION_Handle *cfg)
846 struct GNUNET_IDENTITY_PROVIDER_Handle *h;
848 h = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_Handle);
861 * Cancel an operation. Note that the operation MAY still
862 * be executed; this merely cancels the continuation; if the request
863 * was already transmitted, the service may still choose to complete
866 * @param op operation to cancel
869 GNUNET_IDENTITY_PROVIDER_cancel (struct GNUNET_IDENTITY_PROVIDER_Operation *op)
871 struct GNUNET_IDENTITY_PROVIDER_Handle *h = op->h;
873 GNUNET_CONTAINER_DLL_remove (h->op_head,
881 * Disconnect from service
883 * @param h handle to destroy
886 GNUNET_IDENTITY_PROVIDER_disconnect (struct GNUNET_IDENTITY_PROVIDER_Handle *h)
888 GNUNET_assert (NULL != h);
891 GNUNET_MQ_destroy (h->mq);
894 if (NULL != h->reconnect_task)
896 GNUNET_SCHEDULER_cancel (h->reconnect_task);
897 h->reconnect_task = NULL;
899 GNUNET_assert (NULL == h->op_head);
904 * Store an attribute. If the attribute is already present,
905 * it is replaced with the new attribute.
907 * @param h handle to the identity provider
908 * @param pkey private key of the identity
909 * @param attr the attribute value
910 * @param exp_interval the relative expiration interval for the attribute
911 * @param cont continuation to call when done
912 * @param cont_cls closure for @a cont
913 * @return handle to abort the request
915 struct GNUNET_IDENTITY_PROVIDER_Operation *
916 GNUNET_IDENTITY_PROVIDER_attribute_store (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
917 const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey,
918 const struct GNUNET_IDENTITY_ATTRIBUTE_Claim *attr,
919 const struct GNUNET_TIME_Relative *exp_interval,
920 GNUNET_IDENTITY_PROVIDER_ContinuationWithStatus cont,
923 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
924 struct AttributeStoreMessage *sam;
927 op = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_Operation);
931 op->r_id = h->r_id_gen++;
932 GNUNET_CONTAINER_DLL_insert_tail (h->op_head,
935 attr_len = GNUNET_IDENTITY_ATTRIBUTE_serialize_get_size (attr);
936 op->env = GNUNET_MQ_msg_extra (sam,
938 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_STORE);
939 sam->identity = *pkey;
940 sam->id = htonl (op->r_id);
941 sam->exp = GNUNET_htonll (exp_interval->rel_value_us);
943 GNUNET_IDENTITY_ATTRIBUTE_serialize (attr,
946 sam->attr_len = htons (attr_len);
948 GNUNET_MQ_send_copy (h->mq,
956 * List all attributes for a local identity.
957 * This MUST lock the `struct GNUNET_IDENTITY_PROVIDER_Handle`
958 * for any other calls than #GNUNET_IDENTITY_PROVIDER_get_attributes_next() and
959 * #GNUNET_IDENTITY_PROVIDER_get_attributes_stop. @a proc will be called once
960 * immediately, and then again after
961 * #GNUNET_IDENTITY_PROVIDER_get_attributes_next() is invoked.
963 * On error (disconnect), @a error_cb will be invoked.
964 * On normal completion, @a finish_cb proc will be
967 * @param h handle to the idp
968 * @param identity identity to access
969 * @param error_cb function to call on error (i.e. disconnect),
970 * the handle is afterwards invalid
971 * @param error_cb_cls closure for @a error_cb
972 * @param proc function to call on each attribute; it
973 * will be called repeatedly with a value (if available)
974 * @param proc_cls closure for @a proc
975 * @param finish_cb function to call on completion
976 * the handle is afterwards invalid
977 * @param finish_cb_cls closure for @a finish_cb
978 * @return an iterator handle to use for iteration
980 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *
981 GNUNET_IDENTITY_PROVIDER_get_attributes_start (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
982 const struct GNUNET_CRYPTO_EcdsaPrivateKey *identity,
983 GNUNET_SCHEDULER_TaskCallback error_cb,
985 GNUNET_IDENTITY_PROVIDER_AttributeResult proc,
987 GNUNET_SCHEDULER_TaskCallback finish_cb,
990 struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it;
991 struct GNUNET_MQ_Envelope *env;
992 struct AttributeIterationStartMessage *msg;
996 it = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_AttributeIterator);
998 it->error_cb = error_cb;
999 it->error_cb_cls = error_cb_cls;
1000 it->finish_cb = finish_cb;
1001 it->finish_cb_cls = finish_cb_cls;
1003 it->proc_cls = proc_cls;
1005 it->identity = *identity;
1006 GNUNET_CONTAINER_DLL_insert_tail (h->it_head,
1009 env = GNUNET_MQ_msg (msg,
1010 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_ITERATION_START);
1011 msg->id = htonl (rid);
1012 msg->identity = *identity;
1016 GNUNET_MQ_send (h->mq,
1023 * Calls the record processor specified in #GNUNET_IDENTITY_PROVIDER_get_attributes_start
1024 * for the next record.
1026 * @param it the iterator
1029 GNUNET_IDENTITY_PROVIDER_get_attributes_next (struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it)
1031 struct GNUNET_IDENTITY_PROVIDER_Handle *h = it->h;
1032 struct AttributeIterationNextMessage *msg;
1033 struct GNUNET_MQ_Envelope *env;
1035 env = GNUNET_MQ_msg (msg,
1036 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_ITERATION_NEXT);
1037 msg->id = htonl (it->r_id);
1038 GNUNET_MQ_send (h->mq,
1044 * Stops iteration and releases the idp handle for further calls. Must
1045 * be called on any iteration that has not yet completed prior to calling
1046 * #GNUNET_IDENTITY_PROVIDER_disconnect.
1048 * @param it the iterator
1051 GNUNET_IDENTITY_PROVIDER_get_attributes_stop (struct GNUNET_IDENTITY_PROVIDER_AttributeIterator *it)
1053 struct GNUNET_IDENTITY_PROVIDER_Handle *h = it->h;
1054 struct GNUNET_MQ_Envelope *env;
1055 struct AttributeIterationStopMessage *msg;
1059 env = GNUNET_MQ_msg (msg,
1060 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ATTRIBUTE_ITERATION_STOP);
1061 msg->id = htonl (it->r_id);
1062 GNUNET_MQ_send (h->mq,
1070 * Issues a ticket to another identity. The identity may use
1071 * @GNUNET_IDENTITY_PROVIDER_authorization_ticket_consume to consume the ticket
1072 * and retrieve the attributes specified in the AttributeList.
1074 * @param h the identity provider to use
1075 * @param iss the issuing identity
1076 * @param rp the subject of the ticket (the relying party)
1077 * @param attrs the attributes that the relying party is given access to
1078 * @param cb the callback
1079 * @param cb_cls the callback closure
1080 * @return handle to abort the operation
1082 struct GNUNET_IDENTITY_PROVIDER_Operation *
1083 GNUNET_IDENTITY_PROVIDER_ticket_issue (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
1084 const struct GNUNET_CRYPTO_EcdsaPrivateKey *iss,
1085 const struct GNUNET_CRYPTO_EcdsaPublicKey *rp,
1086 const struct GNUNET_IDENTITY_ATTRIBUTE_ClaimList *attrs,
1087 GNUNET_IDENTITY_PROVIDER_TicketCallback cb,
1090 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
1091 struct IssueTicketMessage *tim;
1094 op = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_Operation);
1098 op->r_id = h->r_id_gen++;
1099 GNUNET_CONTAINER_DLL_insert_tail (h->op_head,
1102 attr_len = GNUNET_IDENTITY_ATTRIBUTE_list_serialize_get_size (attrs);
1103 op->env = GNUNET_MQ_msg_extra (tim,
1105 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_ISSUE_TICKET);
1106 tim->identity = *iss;
1108 tim->id = htonl (op->r_id);
1110 GNUNET_IDENTITY_ATTRIBUTE_list_serialize (attrs,
1113 tim->attr_len = htons (attr_len);
1115 GNUNET_MQ_send_copy (h->mq,
1121 * Consumes an issued ticket. The ticket is persisted
1122 * and used to retrieve identity information from the issuer
1124 * @param h the identity provider to use
1125 * @param identity the identity that is the subject of the issued ticket (the relying party)
1126 * @param ticket the issued ticket to consume
1127 * @param cb the callback to call
1128 * @param cb_cls the callback closure
1129 * @return handle to abort the operation
1131 struct GNUNET_IDENTITY_PROVIDER_Operation *
1132 GNUNET_IDENTITY_PROVIDER_ticket_consume (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
1133 const struct GNUNET_CRYPTO_EcdsaPrivateKey *identity,
1134 const struct GNUNET_IDENTITY_PROVIDER_Ticket *ticket,
1135 GNUNET_IDENTITY_PROVIDER_AttributeResult cb,
1138 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
1139 struct ConsumeTicketMessage *ctm;
1141 op = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_Operation);
1145 op->r_id = h->r_id_gen++;
1146 GNUNET_CONTAINER_DLL_insert_tail (h->op_head,
1149 op->env = GNUNET_MQ_msg_extra (ctm,
1150 sizeof (const struct GNUNET_IDENTITY_PROVIDER_Ticket),
1151 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_CONSUME_TICKET);
1152 ctm->identity = *identity;
1153 ctm->id = htonl (op->r_id);
1155 GNUNET_memcpy ((char*)&ctm[1],
1157 sizeof (const struct GNUNET_IDENTITY_PROVIDER_Ticket));
1160 GNUNET_MQ_send_copy (h->mq,
1168 * Lists all tickets that have been issued to remote
1169 * identites (relying parties)
1171 * @param h the identity provider to use
1172 * @param identity the issuing identity
1173 * @param error_cb function to call on error (i.e. disconnect),
1174 * the handle is afterwards invalid
1175 * @param error_cb_cls closure for @a error_cb
1176 * @param proc function to call on each ticket; it
1177 * will be called repeatedly with a value (if available)
1178 * @param proc_cls closure for @a proc
1179 * @param finish_cb function to call on completion
1180 * the handle is afterwards invalid
1181 * @param finish_cb_cls closure for @a finish_cb
1182 * @return an iterator handle to use for iteration
1184 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *
1185 GNUNET_IDENTITY_PROVIDER_ticket_iteration_start (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
1186 const struct GNUNET_CRYPTO_EcdsaPrivateKey *identity,
1187 GNUNET_SCHEDULER_TaskCallback error_cb,
1189 GNUNET_IDENTITY_PROVIDER_TicketCallback proc,
1191 GNUNET_SCHEDULER_TaskCallback finish_cb,
1192 void *finish_cb_cls)
1194 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *it;
1195 struct GNUNET_CRYPTO_EcdsaPublicKey identity_pub;
1196 struct GNUNET_MQ_Envelope *env;
1197 struct TicketIterationStartMessage *msg;
1200 GNUNET_CRYPTO_ecdsa_key_get_public (identity,
1202 rid = h->r_id_gen++;
1203 it = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_TicketIterator);
1205 it->error_cb = error_cb;
1206 it->error_cb_cls = error_cb_cls;
1207 it->finish_cb = finish_cb;
1208 it->finish_cb_cls = finish_cb_cls;
1212 GNUNET_CONTAINER_DLL_insert_tail (h->ticket_it_head,
1215 env = GNUNET_MQ_msg (msg,
1216 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_ITERATION_START);
1217 msg->id = htonl (rid);
1218 msg->identity = identity_pub;
1219 msg->is_audience = htonl (GNUNET_NO);
1223 GNUNET_MQ_send (h->mq,
1231 * Lists all tickets that have been issued to remote
1232 * identites (relying parties)
1234 * @param h the identity provider to use
1235 * @param identity the issuing identity
1236 * @param error_cb function to call on error (i.e. disconnect),
1237 * the handle is afterwards invalid
1238 * @param error_cb_cls closure for @a error_cb
1239 * @param proc function to call on each ticket; it
1240 * will be called repeatedly with a value (if available)
1241 * @param proc_cls closure for @a proc
1242 * @param finish_cb function to call on completion
1243 * the handle is afterwards invalid
1244 * @param finish_cb_cls closure for @a finish_cb
1245 * @return an iterator handle to use for iteration
1247 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *
1248 GNUNET_IDENTITY_PROVIDER_ticket_iteration_start_rp (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
1249 const struct GNUNET_CRYPTO_EcdsaPublicKey *identity,
1250 GNUNET_SCHEDULER_TaskCallback error_cb,
1252 GNUNET_IDENTITY_PROVIDER_TicketCallback proc,
1254 GNUNET_SCHEDULER_TaskCallback finish_cb,
1255 void *finish_cb_cls)
1257 struct GNUNET_IDENTITY_PROVIDER_TicketIterator *it;
1258 struct GNUNET_MQ_Envelope *env;
1259 struct TicketIterationStartMessage *msg;
1262 rid = h->r_id_gen++;
1263 it = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_TicketIterator);
1265 it->error_cb = error_cb;
1266 it->error_cb_cls = error_cb_cls;
1267 it->finish_cb = finish_cb;
1268 it->finish_cb_cls = finish_cb_cls;
1272 GNUNET_CONTAINER_DLL_insert_tail (h->ticket_it_head,
1275 env = GNUNET_MQ_msg (msg,
1276 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_ITERATION_START);
1277 msg->id = htonl (rid);
1278 msg->identity = *identity;
1279 msg->is_audience = htonl (GNUNET_YES);
1283 GNUNET_MQ_send (h->mq,
1291 * Calls the record processor specified in #GNUNET_IDENTITY_PROVIDER_ticket_iteration_start
1292 * for the next record.
1294 * @param it the iterator
1297 GNUNET_IDENTITY_PROVIDER_ticket_iteration_next (struct GNUNET_IDENTITY_PROVIDER_TicketIterator *it)
1299 struct GNUNET_IDENTITY_PROVIDER_Handle *h = it->h;
1300 struct TicketIterationNextMessage *msg;
1301 struct GNUNET_MQ_Envelope *env;
1303 env = GNUNET_MQ_msg (msg,
1304 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_ITERATION_NEXT);
1305 msg->id = htonl (it->r_id);
1306 GNUNET_MQ_send (h->mq,
1312 * Stops iteration and releases the idp handle for further calls. Must
1313 * be called on any iteration that has not yet completed prior to calling
1314 * #GNUNET_IDENTITY_PROVIDER_disconnect.
1316 * @param it the iterator
1319 GNUNET_IDENTITY_PROVIDER_ticket_iteration_stop (struct GNUNET_IDENTITY_PROVIDER_TicketIterator *it)
1321 struct GNUNET_IDENTITY_PROVIDER_Handle *h = it->h;
1322 struct GNUNET_MQ_Envelope *env;
1323 struct TicketIterationStopMessage *msg;
1327 env = GNUNET_MQ_msg (msg,
1328 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_TICKET_ITERATION_STOP);
1329 msg->id = htonl (it->r_id);
1330 GNUNET_MQ_send (h->mq,
1337 * Revoked an issued ticket. The relying party will be unable to retrieve
1338 * updated attributes.
1340 * @param h the identity provider to use
1341 * @param identity the issuing identity
1342 * @param ticket the ticket to revoke
1343 * @param cb the callback
1344 * @param cb_cls the callback closure
1345 * @return handle to abort the operation
1347 struct GNUNET_IDENTITY_PROVIDER_Operation *
1348 GNUNET_IDENTITY_PROVIDER_ticket_revoke (struct GNUNET_IDENTITY_PROVIDER_Handle *h,
1349 const struct GNUNET_CRYPTO_EcdsaPrivateKey *identity,
1350 const struct GNUNET_IDENTITY_PROVIDER_Ticket *ticket,
1351 GNUNET_IDENTITY_PROVIDER_ContinuationWithStatus cb,
1354 struct GNUNET_IDENTITY_PROVIDER_Operation *op;
1355 struct GNUNET_MQ_Envelope *env;
1356 struct RevokeTicketMessage *msg;
1359 rid = h->r_id_gen++;
1360 op = GNUNET_new (struct GNUNET_IDENTITY_PROVIDER_Operation);
1365 GNUNET_CONTAINER_DLL_insert_tail (h->op_head,
1368 env = GNUNET_MQ_msg_extra (msg,
1369 sizeof (struct GNUNET_IDENTITY_PROVIDER_Ticket),
1370 GNUNET_MESSAGE_TYPE_IDENTITY_PROVIDER_REVOKE_TICKET);
1371 msg->id = htonl (rid);
1372 msg->identity = *identity;
1373 GNUNET_memcpy (&msg[1],
1375 sizeof (struct GNUNET_IDENTITY_PROVIDER_Ticket));
1379 GNUNET_MQ_send (h->mq,
1386 /* end of identity_provider_api.c */