aboutsummaryrefslogtreecommitdiff
path: root/src/secretsharing/gnunet-service-secretsharing.c
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2017-03-14 00:53:02 +0100
committerChristian Grothoff <christian@grothoff.org>2017-03-14 00:53:02 +0100
commita015c3df2059a98a8692e7f2b06038e066bbc916 (patch)
tree29089dba01927d3975423c7e7cbbd242e0aaf01c /src/secretsharing/gnunet-service-secretsharing.c
parent8d71f909cb22fbf6774e4042309a8eb133af3bfc (diff)
downloadgnunet-a015c3df2059a98a8692e7f2b06038e066bbc916.tar.gz
gnunet-a015c3df2059a98a8692e7f2b06038e066bbc916.zip
migrate secretsharing to new service API
Diffstat (limited to 'src/secretsharing/gnunet-service-secretsharing.c')
-rw-r--r--src/secretsharing/gnunet-service-secretsharing.c511
1 files changed, 262 insertions, 249 deletions
diff --git a/src/secretsharing/gnunet-service-secretsharing.c b/src/secretsharing/gnunet-service-secretsharing.c
index ddbe81576..fa35dc21b 100644
--- a/src/secretsharing/gnunet-service-secretsharing.c
+++ b/src/secretsharing/gnunet-service-secretsharing.c
@@ -109,19 +109,16 @@ struct DecryptPeerInfo
109 109
110 110
111/** 111/**
112 * State we keep per client.
113 */
114struct ClientState;
115
116
117/**
112 * Session to establish a threshold-shared secret. 118 * Session to establish a threshold-shared secret.
113 */ 119 */
114struct KeygenSession 120struct KeygenSession
115{ 121{
116 /**
117 * Keygen sessions are held in a linked list.
118 */
119 struct KeygenSession *next;
120
121 /**
122 * Keygen sessions are held in a linked list.
123 */
124 struct KeygenSession *prev;
125 122
126 /** 123 /**
127 * Current consensus, used for both DKG rounds. 124 * Current consensus, used for both DKG rounds.
@@ -129,15 +126,9 @@ struct KeygenSession
129 struct GNUNET_CONSENSUS_Handle *consensus; 126 struct GNUNET_CONSENSUS_Handle *consensus;
130 127
131 /** 128 /**
132 * Client that is interested in the result 129 * Which client is this for?
133 * of this key generation session.
134 */
135 struct GNUNET_SERVER_Client *client;
136
137 /**
138 * Message queue for 'client'
139 */ 130 */
140 struct GNUNET_MQ_Handle *client_mq; 131 struct ClientState *cs;
141 132
142 /** 133 /**
143 * Randomly generated coefficients of the polynomial for sharing our 134 * Randomly generated coefficients of the polynomial for sharing our
@@ -223,15 +214,6 @@ struct KeygenSession
223 */ 214 */
224struct DecryptSession 215struct DecryptSession
225{ 216{
226 /**
227 * Decrypt sessions are stored in a linked list.
228 */
229 struct DecryptSession *next;
230
231 /**
232 * Decrypt sessions are stored in a linked list.
233 */
234 struct DecryptSession *prev;
235 217
236 /** 218 /**
237 * Handle to the consensus over partial decryptions. 219 * Handle to the consensus over partial decryptions.
@@ -239,14 +221,9 @@ struct DecryptSession
239 struct GNUNET_CONSENSUS_Handle *consensus; 221 struct GNUNET_CONSENSUS_Handle *consensus;
240 222
241 /** 223 /**
242 * Client connected to us. 224 * Which client is this for?
243 */ 225 */
244 struct GNUNET_SERVER_Client *client; 226 struct ClientState *cs;
245
246 /**
247 * Message queue for 'client'.
248 */
249 struct GNUNET_MQ_Handle *client_mq;
250 227
251 /** 228 /**
252 * When should we start communicating for decryption? 229 * When should we start communicating for decryption?
@@ -279,24 +256,32 @@ struct DecryptSession
279 256
280 257
281/** 258/**
282 * Decrypt sessions are held in a linked list. 259 * State we keep per client.
283 */ 260 */
284static struct DecryptSession *decrypt_sessions_head; 261struct ClientState
262{
263 /**
264 * Decrypt session of the client, if any.
265 */
266 struct DecryptSession *decrypt_session;
285 267
286/** 268 /**
287 * Decrypt sessions are held in a linked list. 269 * Keygen session of the client, if any.
288 */ 270 */
289static struct DecryptSession *decrypt_sessions_tail; 271 struct KeygenSession *keygen_session;
290 272
291/** 273 /**
292 * Decrypt sessions are held in a linked list. 274 * Client this is about.
293 */ 275 */
294static struct KeygenSession *keygen_sessions_head; 276 struct GNUNET_SERVICE_Client *client;
277
278 /**
279 * MQ to talk to @a client.
280 */
281 struct GNUNET_MQ_Handle *mq;
282
283};
295 284
296/**
297 * Decrypt sessions are held in a linked list.
298 */
299static struct KeygenSession *keygen_sessions_tail;
300 285
301/** 286/**
302 * The ElGamal prime field order as libgcrypt mpi. 287 * The ElGamal prime field order as libgcrypt mpi.
@@ -331,11 +316,6 @@ static struct GNUNET_CRYPTO_EddsaPrivateKey *my_peer_private_key;
331 */ 316 */
332static const struct GNUNET_CONFIGURATION_Handle *cfg; 317static const struct GNUNET_CONFIGURATION_Handle *cfg;
333 318
334/**
335 * Server for this service.
336 */
337static struct GNUNET_SERVER_Handle *srv;
338
339 319
340/** 320/**
341 * Get the peer info belonging to a peer identity in a keygen session. 321 * Get the peer info belonging to a peer identity in a keygen session.
@@ -468,7 +448,8 @@ normalize_peers (struct GNUNET_PeerIdentity *listed,
468 n += 1; 448 n += 1;
469 } 449 }
470 450
471 normalized = GNUNET_new_array (n, struct GNUNET_PeerIdentity); 451 normalized = GNUNET_new_array (n,
452 struct GNUNET_PeerIdentity);
472 453
473 if (GNUNET_NO == local_peer_in_list) 454 if (GNUNET_NO == local_peer_in_list)
474 normalized[n - 1] = my_peer; 455 normalized[n - 1] = my_peer;
@@ -558,10 +539,13 @@ compute_lagrange_coefficient (gcry_mpi_t coeff, unsigned int j,
558static void 539static void
559decrypt_session_destroy (struct DecryptSession *ds) 540decrypt_session_destroy (struct DecryptSession *ds)
560{ 541{
561 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying decrypt session\n"); 542 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
562 543 "destroying decrypt session\n");
563 GNUNET_CONTAINER_DLL_remove (decrypt_sessions_head, decrypt_sessions_tail, ds); 544 if (NULL != ds->cs)
564 545 {
546 ds->cs->decrypt_session = NULL;
547 ds->cs = NULL;
548 }
565 if (NULL != ds->consensus) 549 if (NULL != ds->consensus)
566 { 550 {
567 GNUNET_CONSENSUS_destroy (ds->consensus); 551 GNUNET_CONSENSUS_destroy (ds->consensus);
@@ -570,8 +554,7 @@ decrypt_session_destroy (struct DecryptSession *ds)
570 554
571 if (NULL != ds->info) 555 if (NULL != ds->info)
572 { 556 {
573 unsigned int i; 557 for (unsigned int i = 0; i < ds->share->num_peers; i++)
574 for (i = 0; i < ds->share->num_peers; i++)
575 { 558 {
576 if (NULL != ds->info[i].partial_decryption) 559 if (NULL != ds->info[i].partial_decryption)
577 { 560 {
@@ -582,26 +565,12 @@ decrypt_session_destroy (struct DecryptSession *ds)
582 GNUNET_free (ds->info); 565 GNUNET_free (ds->info);
583 ds->info = NULL; 566 ds->info = NULL;
584 } 567 }
585
586 if (NULL != ds->share) 568 if (NULL != ds->share)
587 { 569 {
588 GNUNET_SECRETSHARING_share_destroy (ds->share); 570 GNUNET_SECRETSHARING_share_destroy (ds->share);
589 ds->share = NULL; 571 ds->share = NULL;
590 } 572 }
591 573
592 if (NULL != ds->client_mq)
593 {
594 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying decrypt MQ\n");
595 GNUNET_MQ_destroy (ds->client_mq);
596 ds->client_mq = NULL;
597 }
598
599 if (NULL != ds->client)
600 {
601 GNUNET_SERVER_client_disconnect (ds->client);
602 ds->client = NULL;
603 }
604
605 GNUNET_free (ds); 574 GNUNET_free (ds);
606} 575}
607 576
@@ -630,14 +599,17 @@ keygen_info_destroy (struct KeygenPeerInfo *info)
630static void 599static void
631keygen_session_destroy (struct KeygenSession *ks) 600keygen_session_destroy (struct KeygenSession *ks)
632{ 601{
633 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying keygen session\n"); 602 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
634 603 "destroying keygen session\n");
635 GNUNET_CONTAINER_DLL_remove (keygen_sessions_head, keygen_sessions_tail, ks);
636 604
605 if (NULL != ks->cs)
606 {
607 ks->cs->keygen_session = NULL;
608 ks->cs = NULL;
609 }
637 if (NULL != ks->info) 610 if (NULL != ks->info)
638 { 611 {
639 unsigned int i; 612 for (unsigned int i = 0; i < ks->num_peers; i++)
640 for (i = 0; i < ks->num_peers; i++)
641 keygen_info_destroy (&ks->info[i]); 613 keygen_info_destroy (&ks->info[i]);
642 GNUNET_free (ks->info); 614 GNUNET_free (ks->info);
643 ks->info = NULL; 615 ks->info = NULL;
@@ -651,8 +623,7 @@ keygen_session_destroy (struct KeygenSession *ks)
651 623
652 if (NULL != ks->presecret_polynomial) 624 if (NULL != ks->presecret_polynomial)
653 { 625 {
654 unsigned int i; 626 for (unsigned int i = 0; i < ks->threshold; i++)
655 for (i = 0; i < ks->threshold; i++)
656 { 627 {
657 GNUNET_assert (NULL != ks->presecret_polynomial[i]); 628 GNUNET_assert (NULL != ks->presecret_polynomial[i]);
658 gcry_mpi_release (ks->presecret_polynomial[i]); 629 gcry_mpi_release (ks->presecret_polynomial[i]);
@@ -661,38 +632,21 @@ keygen_session_destroy (struct KeygenSession *ks)
661 GNUNET_free (ks->presecret_polynomial); 632 GNUNET_free (ks->presecret_polynomial);
662 ks->presecret_polynomial = NULL; 633 ks->presecret_polynomial = NULL;
663 } 634 }
664
665 if (NULL != ks->client_mq)
666 {
667 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying keygen MQ\n");
668 GNUNET_MQ_destroy (ks->client_mq);
669 ks->client_mq = NULL;
670 }
671
672 if (NULL != ks->my_share) 635 if (NULL != ks->my_share)
673 { 636 {
674 gcry_mpi_release (ks->my_share); 637 gcry_mpi_release (ks->my_share);
675 ks->my_share = NULL; 638 ks->my_share = NULL;
676 } 639 }
677
678 if (NULL != ks->public_key) 640 if (NULL != ks->public_key)
679 { 641 {
680 gcry_mpi_release (ks->public_key); 642 gcry_mpi_release (ks->public_key);
681 ks->public_key = NULL; 643 ks->public_key = NULL;
682 } 644 }
683
684 if (NULL != ks->peers) 645 if (NULL != ks->peers)
685 { 646 {
686 GNUNET_free (ks->peers); 647 GNUNET_free (ks->peers);
687 ks->peers = NULL; 648 ks->peers = NULL;
688 } 649 }
689
690 if (NULL != ks->client)
691 {
692 GNUNET_SERVER_client_disconnect (ks->client);
693 ks->client = NULL;
694 }
695
696 GNUNET_free (ks); 650 GNUNET_free (ks);
697} 651}
698 652
@@ -706,11 +660,7 @@ keygen_session_destroy (struct KeygenSession *ks)
706static void 660static void
707cleanup_task (void *cls) 661cleanup_task (void *cls)
708{ 662{
709 while (NULL != decrypt_sessions_head) 663 /* Nothing to do! */
710 decrypt_session_destroy (decrypt_sessions_head);
711
712 while (NULL != keygen_sessions_head)
713 keygen_session_destroy (keygen_sessions_head);
714} 664}
715 665
716 666
@@ -727,7 +677,8 @@ generate_presecret_polynomial (struct KeygenSession *ks)
727 gcry_mpi_t v; 677 gcry_mpi_t v;
728 678
729 GNUNET_assert (NULL == ks->presecret_polynomial); 679 GNUNET_assert (NULL == ks->presecret_polynomial);
730 ks->presecret_polynomial = GNUNET_new_array (ks->threshold, gcry_mpi_t); 680 ks->presecret_polynomial = GNUNET_new_array (ks->threshold,
681 gcry_mpi_t);
731 for (i = 0; i < ks->threshold; i++) 682 for (i = 0; i < ks->threshold; i++)
732 { 683 {
733 v = ks->presecret_polynomial[i] = gcry_mpi_new (GNUNET_SECRETSHARING_ELGAMAL_BITS); 684 v = ks->presecret_polynomial[i] = gcry_mpi_new (GNUNET_SECRETSHARING_ELGAMAL_BITS);
@@ -855,10 +806,13 @@ keygen_round2_conclude (void *cls)
855 if (GNUNET_YES == ks->info[i].round2_valid) 806 if (GNUNET_YES == ks->info[i].round2_valid)
856 share->num_peers++; 807 share->num_peers++;
857 808
858 share->peers = GNUNET_new_array (share->num_peers, struct GNUNET_PeerIdentity); 809 share->peers = GNUNET_new_array (share->num_peers,
810 struct GNUNET_PeerIdentity);
859 share->sigmas = 811 share->sigmas =
860 GNUNET_new_array (share->num_peers, struct GNUNET_SECRETSHARING_FieldElement); 812 GNUNET_new_array (share->num_peers,
861 share->original_indices = GNUNET_new_array (share->num_peers, uint16_t); 813 struct GNUNET_SECRETSHARING_FieldElement);
814 share->original_indices = GNUNET_new_array (share->num_peers,
815 uint16_t);
862 816
863 /* maybe we're not even in the list of peers? */ 817 /* maybe we're not even in the list of peers? */
864 share->my_peer = share->num_peers; 818 share->my_peer = share->num_peers;
@@ -907,7 +861,8 @@ keygen_round2_conclude (void *cls)
907 GNUNET_SECRETSHARING_share_destroy (share); 861 GNUNET_SECRETSHARING_share_destroy (share);
908 share = NULL; 862 share = NULL;
909 863
910 GNUNET_MQ_send (ks->client_mq, ev); 864 GNUNET_MQ_send (ks->cs->mq,
865 ev);
911} 866}
912 867
913 868
@@ -1669,73 +1624,102 @@ insert_round1_element (struct KeygenSession *ks)
1669 1624
1670 1625
1671/** 1626/**
1627 * Check that @a msg is well-formed.
1628 *
1629 * @param cls identification of the client
1630 * @param msg the actual message
1631 * @return #GNUNET_OK if @a msg is well-formed
1632 */
1633static int
1634check_client_keygen (void *cls,
1635 const struct GNUNET_SECRETSHARING_CreateMessage *msg)
1636{
1637 unsigned int num_peers = ntohs (msg->num_peers);
1638
1639 if (ntohs (msg->header.size) - sizeof (*msg) !=
1640 num_peers * sizeof (struct GNUNET_PeerIdentity))
1641 {
1642 GNUNET_break (0);
1643 return GNUNET_SYSERR;
1644 }
1645 return GNUNET_OK;
1646}
1647
1648
1649/**
1672 * Functions with this signature are called whenever a message is 1650 * Functions with this signature are called whenever a message is
1673 * received. 1651 * received.
1674 * 1652 *
1675 * @param cls closure 1653 * @param cls identification of the client
1676 * @param client identification of the client 1654 * @param msg the actual message
1677 * @param message the actual message
1678 */ 1655 */
1679static void handle_client_keygen (void *cls, 1656static void
1680 struct GNUNET_SERVER_Client *client, 1657handle_client_keygen (void *cls,
1681 const struct GNUNET_MessageHeader 1658 const struct GNUNET_SECRETSHARING_CreateMessage *msg)
1682 *message)
1683{ 1659{
1684 const struct GNUNET_SECRETSHARING_CreateMessage *msg = 1660 struct ClientState *cs = cls;
1685 (const struct GNUNET_SECRETSHARING_CreateMessage *) message;
1686 struct KeygenSession *ks; 1661 struct KeygenSession *ks;
1687 unsigned int i;
1688
1689 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "client requested key generation\n");
1690 1662
1663 GNUNET_log (GNUNET_ERROR_TYPE_INFO,
1664 "client requested key generation\n");
1665 if (NULL != cs->keygen_session)
1666 {
1667 GNUNET_break (0);
1668 GNUNET_SERVICE_client_drop (cs->client);
1669 return;
1670 }
1691 ks = GNUNET_new (struct KeygenSession); 1671 ks = GNUNET_new (struct KeygenSession);
1692 1672 ks->cs = cs;
1693 /* FIXME: check if client already has some session */ 1673 cs->keygen_session = ks;
1694
1695 GNUNET_CONTAINER_DLL_insert (keygen_sessions_head, keygen_sessions_tail, ks);
1696
1697 ks->client = client;
1698 ks->client_mq = GNUNET_MQ_queue_for_server_client (client);
1699
1700 ks->deadline = GNUNET_TIME_absolute_ntoh (msg->deadline); 1674 ks->deadline = GNUNET_TIME_absolute_ntoh (msg->deadline);
1701 ks->threshold = ntohs (msg->threshold); 1675 ks->threshold = ntohs (msg->threshold);
1702 ks->num_peers = ntohs (msg->num_peers); 1676 ks->num_peers = ntohs (msg->num_peers);
1703 1677
1704 ks->peers = normalize_peers ((struct GNUNET_PeerIdentity *) &msg[1], ks->num_peers, 1678 ks->peers = normalize_peers ((struct GNUNET_PeerIdentity *) &msg[1],
1705 &ks->num_peers, &ks->local_peer_idx); 1679 ks->num_peers,
1680 &ks->num_peers,
1681 &ks->local_peer_idx);
1706 1682
1707 1683
1708 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "first round of consensus with %u peers\n", ks->num_peers); 1684 GNUNET_log (GNUNET_ERROR_TYPE_INFO,
1709 ks->consensus = GNUNET_CONSENSUS_create (cfg, ks->num_peers, ks->peers, &msg->session_id, 1685 "first round of consensus with %u peers\n",
1686 ks->num_peers);
1687 ks->consensus = GNUNET_CONSENSUS_create (cfg,
1688 ks->num_peers,
1689 ks->peers,
1690 &msg->session_id,
1710 GNUNET_TIME_absolute_ntoh (msg->start), 1691 GNUNET_TIME_absolute_ntoh (msg->start),
1711 GNUNET_TIME_absolute_ntoh (msg->deadline), 1692 GNUNET_TIME_absolute_ntoh (msg->deadline),
1712 keygen_round1_new_element, ks); 1693 keygen_round1_new_element,
1694 ks);
1713 1695
1714 ks->info = GNUNET_new_array (ks->num_peers, struct KeygenPeerInfo); 1696 ks->info = GNUNET_new_array (ks->num_peers,
1697 struct KeygenPeerInfo);
1715 1698
1716 for (i = 0; i < ks->num_peers; i++) 1699 for (unsigned int i = 0; i < ks->num_peers; i++)
1717 ks->info[i].peer = ks->peers[i]; 1700 ks->info[i].peer = ks->peers[i];
1718 1701
1719 GNUNET_CRYPTO_paillier_create (&ks->info[ks->local_peer_idx].paillier_public_key, 1702 GNUNET_CRYPTO_paillier_create (&ks->info[ks->local_peer_idx].paillier_public_key,
1720 &ks->paillier_private_key); 1703 &ks->paillier_private_key);
1721 1704
1722 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "P%u: Generated paillier key pair\n", ks->local_peer_idx); 1705 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1723 1706 "P%u: Generated paillier key pair\n",
1707 ks->local_peer_idx);
1724 generate_presecret_polynomial (ks); 1708 generate_presecret_polynomial (ks);
1725 1709 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1726 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "P%u: Generated presecret polynomial\n", ks->local_peer_idx); 1710 "P%u: Generated presecret polynomial\n",
1727 1711 ks->local_peer_idx);
1728 insert_round1_element (ks); 1712 insert_round1_element (ks);
1729 1713 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1730 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "P%u: Concluding for round 1\n", ks->local_peer_idx); 1714 "P%u: Concluding for round 1\n",
1731 1715 ks->local_peer_idx);
1732 GNUNET_CONSENSUS_conclude (ks->consensus, 1716 GNUNET_CONSENSUS_conclude (ks->consensus,
1733 keygen_round1_conclude, 1717 keygen_round1_conclude,
1734 ks); 1718 ks);
1735 1719 GNUNET_SERVICE_client_continue (cs->client);
1736 GNUNET_SERVER_receive_done (client, GNUNET_OK); 1720 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1737 1721 "P%u: Waiting for round 1 elements ...\n",
1738 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "P%u: Waiting for round 1 elements ...\n", ks->local_peer_idx); 1722 ks->local_peer_idx);
1739} 1723}
1740 1724
1741 1725
@@ -1771,20 +1755,24 @@ decrypt_conclude (void *cls)
1771 if (NULL != ds->info[i].partial_decryption) 1755 if (NULL != ds->info[i].partial_decryption)
1772 num++; 1756 num++;
1773 1757
1774 indices = GNUNET_malloc (num * sizeof (unsigned int)); 1758 indices = GNUNET_new_array (num,
1759 unsigned int);
1775 j = 0; 1760 j = 0;
1776 for (i = 0; i < ds->share->num_peers; i++) 1761 for (i = 0; i < ds->share->num_peers; i++)
1777 if (NULL != ds->info[i].partial_decryption) 1762 if (NULL != ds->info[i].partial_decryption)
1778 indices[j++] = ds->info[i].original_index; 1763 indices[j++] = ds->info[i].original_index;
1779 1764
1780 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "P%u: decrypt conclude, with %u peers\n", 1765 GNUNET_log (GNUNET_ERROR_TYPE_INFO,
1781 ds->share->my_peer, num); 1766 "P%u: decrypt conclude, with %u peers\n",
1767 ds->share->my_peer,
1768 num);
1782 1769
1783 gcry_mpi_set_ui (prod, 1); 1770 gcry_mpi_set_ui (prod, 1);
1784 for (i = 0; i < num; i++) 1771 for (i = 0; i < num; i++)
1785 { 1772 {
1786 1773
1787 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "P%u: index of %u: %u\n", 1774 GNUNET_log (GNUNET_ERROR_TYPE_INFO,
1775 "P%u: index of %u: %u\n",
1788 ds->share->my_peer, i, indices[i]); 1776 ds->share->my_peer, i, indices[i]);
1789 compute_lagrange_coefficient (lagrange, indices[i], indices, num); 1777 compute_lagrange_coefficient (lagrange, indices[i], indices, num);
1790 // w_i^{\lambda_i} 1778 // w_i^{\lambda_i}
@@ -1801,7 +1789,8 @@ decrypt_conclude (void *cls)
1801 ev = GNUNET_MQ_msg (msg, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT_DONE); 1789 ev = GNUNET_MQ_msg (msg, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT_DONE);
1802 GNUNET_CRYPTO_mpi_print_unsigned (&msg->plaintext, GNUNET_SECRETSHARING_ELGAMAL_BITS / 8, m); 1790 GNUNET_CRYPTO_mpi_print_unsigned (&msg->plaintext, GNUNET_SECRETSHARING_ELGAMAL_BITS / 8, m);
1803 msg->success = htonl (1); 1791 msg->success = htonl (1);
1804 GNUNET_MQ_send (ds->client_mq, ev); 1792 GNUNET_MQ_send (ds->cs->mq,
1793 ev);
1805 1794
1806 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "sent decrypt done to client\n"); 1795 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "sent decrypt done to client\n");
1807 1796
@@ -2100,40 +2089,63 @@ insert_decrypt_element (struct DecryptSession *ds)
2100 2089
2101 2090
2102/** 2091/**
2092 * Check that @a msg is well-formed.
2093 *
2094 * @param cls identification of the client
2095 * @param msg the actual message
2096 * @return #GNUNET_OK (check deferred a bit)
2097 */
2098static int
2099check_client_decrypt (void *cls,
2100 const struct GNUNET_SECRETSHARING_DecryptRequestMessage *msg)
2101{
2102 /* we check later, it's complicated */
2103 return GNUNET_OK;
2104}
2105
2106
2107/**
2103 * Functions with this signature are called whenever a message is 2108 * Functions with this signature are called whenever a message is
2104 * received. 2109 * received.
2105 * 2110 *
2106 * @param cls closure 2111 * @param cls identification of the client
2107 * @param client identification of the client 2112 * @param msg the actual message
2108 * @param message the actual message
2109 */ 2113 */
2110static void handle_client_decrypt (void *cls, 2114static void
2111 struct GNUNET_SERVER_Client *client, 2115handle_client_decrypt (void *cls,
2112 const struct GNUNET_MessageHeader 2116 const struct GNUNET_SECRETSHARING_DecryptRequestMessage *msg)
2113 *message)
2114{ 2117{
2115 const struct GNUNET_SECRETSHARING_DecryptRequestMessage *msg = 2118 struct ClientState *cs = cls;
2116 (const void *) message;
2117 struct DecryptSession *ds; 2119 struct DecryptSession *ds;
2118 struct GNUNET_HashCode session_id; 2120 struct GNUNET_HashCode session_id;
2119 unsigned int i;
2120 2121
2122 if (NULL != cs->decrypt_session)
2123 {
2124 GNUNET_break (0);
2125 GNUNET_SERVICE_client_drop (cs->client);
2126 return;
2127 }
2121 ds = GNUNET_new (struct DecryptSession); 2128 ds = GNUNET_new (struct DecryptSession);
2122 // FIXME: check if session already exists 2129 cs->decrypt_session = ds;
2123 GNUNET_CONTAINER_DLL_insert (decrypt_sessions_head, decrypt_sessions_tail, ds); 2130 ds->cs = cs;
2124 ds->client = client;
2125 ds->client_mq = GNUNET_MQ_queue_for_server_client (client);
2126 ds->start = GNUNET_TIME_absolute_ntoh (msg->start); 2131 ds->start = GNUNET_TIME_absolute_ntoh (msg->start);
2127 ds->deadline = GNUNET_TIME_absolute_ntoh (msg->deadline); 2132 ds->deadline = GNUNET_TIME_absolute_ntoh (msg->deadline);
2128 ds->ciphertext = msg->ciphertext; 2133 ds->ciphertext = msg->ciphertext;
2129 2134
2130 ds->share = GNUNET_SECRETSHARING_share_read (&msg[1], ntohs (msg->header.size) - sizeof *msg, NULL); 2135 ds->share = GNUNET_SECRETSHARING_share_read (&msg[1],
2131 // FIXME: probably should be break rather than assert 2136 ntohs (msg->header.size) - sizeof (*msg),
2132 GNUNET_assert (NULL != ds->share); 2137 NULL);
2133 2138 if (NULL == ds->share)
2134 // FIXME: this is probably sufficient, but kdf/hash with all values would be nicer ... 2139 {
2135 GNUNET_CRYPTO_hash (&msg->ciphertext, sizeof (struct GNUNET_SECRETSHARING_Ciphertext), &session_id); 2140 GNUNET_break (0);
2141 GNUNET_SERVICE_client_drop (cs->client);
2142 return;
2143 }
2136 2144
2145 /* FIXME: this is probably sufficient, but kdf/hash with all values would be nicer ... */
2146 GNUNET_CRYPTO_hash (&msg->ciphertext,
2147 sizeof (struct GNUNET_SECRETSHARING_Ciphertext),
2148 &session_id);
2137 ds->consensus = GNUNET_CONSENSUS_create (cfg, 2149 ds->consensus = GNUNET_CONSENSUS_create (cfg,
2138 ds->share->num_peers, 2150 ds->share->num_peers,
2139 ds->share->peers, 2151 ds->share->peers,
@@ -2144,20 +2156,20 @@ static void handle_client_decrypt (void *cls,
2144 ds); 2156 ds);
2145 2157
2146 2158
2147 ds->info = GNUNET_new_array (ds->share->num_peers, struct DecryptPeerInfo); 2159 ds->info = GNUNET_new_array (ds->share->num_peers,
2148 for (i = 0; i < ds->share->num_peers; i++) 2160 struct DecryptPeerInfo);
2161 for (unsigned int i = 0; i < ds->share->num_peers; i++)
2149 { 2162 {
2150 ds->info[i].peer = ds->share->peers[i]; 2163 ds->info[i].peer = ds->share->peers[i];
2151 ds->info[i].original_index = ds->share->original_indices[i]; 2164 ds->info[i].original_index = ds->share->original_indices[i];
2152 } 2165 }
2153
2154 insert_decrypt_element (ds); 2166 insert_decrypt_element (ds);
2155 2167 GNUNET_CONSENSUS_conclude (ds->consensus,
2156 GNUNET_CONSENSUS_conclude (ds->consensus, decrypt_conclude, ds); 2168 decrypt_conclude,
2157 2169 ds);
2158 GNUNET_SERVER_receive_done (client, GNUNET_OK); 2170 GNUNET_SERVICE_client_continue (cs->client);
2159 2171 GNUNET_log (GNUNET_ERROR_TYPE_INFO,
2160 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "decrypting with %u peers\n", 2172 "decrypting with %u peers\n",
2161 ds->share->num_peers); 2173 ds->share->num_peers);
2162} 2174}
2163 2175
@@ -2174,103 +2186,104 @@ init_crypto_constants (void)
2174} 2186}
2175 2187
2176 2188
2177static struct KeygenSession *
2178keygen_session_get (struct GNUNET_SERVER_Client *client)
2179{
2180 struct KeygenSession *ks;
2181 for (ks = keygen_sessions_head; NULL != ks; ks = ks->next)
2182 if (ks->client == client)
2183 return ks;
2184 return NULL;
2185}
2186
2187static struct DecryptSession *
2188decrypt_session_get (struct GNUNET_SERVER_Client *client)
2189{
2190 struct DecryptSession *ds;
2191 for (ds = decrypt_sessions_head; NULL != ds; ds = ds->next)
2192 if (ds->client == client)
2193 return ds;
2194 return NULL;
2195}
2196
2197
2198/** 2189/**
2199 * Clean up after a client has disconnected 2190 * Initialize secretsharing service.
2200 *
2201 * @param cls closure, unused
2202 * @param client the client to clean up after
2203 */
2204static void
2205handle_client_disconnect (void *cls, struct GNUNET_SERVER_Client *client)
2206{
2207 struct KeygenSession *ks;
2208 struct DecryptSession *ds;
2209
2210 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "handling client disconnect\n");
2211
2212 ks = keygen_session_get (client);
2213 if (NULL != ks)
2214 keygen_session_destroy (ks);
2215
2216 ds = decrypt_session_get (client);
2217 if (NULL != ds)
2218 decrypt_session_destroy (ds);
2219}
2220
2221
2222/**
2223 * Process template requests.
2224 * 2191 *
2225 * @param cls closure 2192 * @param cls closure
2226 * @param server the initialized server
2227 * @param c configuration to use 2193 * @param c configuration to use
2194 * @param service the initialized service
2228 */ 2195 */
2229static void 2196static void
2230run (void *cls, struct GNUNET_SERVER_Handle *server, 2197run (void *cls,
2231 const struct GNUNET_CONFIGURATION_Handle *c) 2198 const struct GNUNET_CONFIGURATION_Handle *c,
2199 struct GNUNET_SERVICE_Handle *service)
2232{ 2200{
2233 static const struct GNUNET_SERVER_MessageHandler handlers[] = {
2234 {handle_client_keygen, NULL, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE, 0},
2235 {handle_client_decrypt, NULL, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT, 0},
2236 {NULL, NULL, 0, 0}
2237 };
2238 cfg = c; 2201 cfg = c;
2239 srv = server;
2240 my_peer_private_key = GNUNET_CRYPTO_eddsa_key_create_from_configuration (c); 2202 my_peer_private_key = GNUNET_CRYPTO_eddsa_key_create_from_configuration (c);
2241 if (NULL == my_peer_private_key) 2203 if (NULL == my_peer_private_key)
2242 { 2204 {
2243 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "could not access host private key\n"); 2205 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
2206 "could not access host private key\n");
2244 GNUNET_break (0); 2207 GNUNET_break (0);
2245 GNUNET_SCHEDULER_shutdown (); 2208 GNUNET_SCHEDULER_shutdown ();
2246 return; 2209 return;
2247 } 2210 }
2248 init_crypto_constants (); 2211 init_crypto_constants ();
2249 if (GNUNET_OK != GNUNET_CRYPTO_get_peer_identity (cfg, &my_peer)) 2212 if (GNUNET_OK !=
2213 GNUNET_CRYPTO_get_peer_identity (cfg,
2214 &my_peer))
2250 { 2215 {
2251 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "could not retrieve host identity\n"); 2216 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
2217 "could not retrieve host identity\n");
2252 GNUNET_break (0); 2218 GNUNET_break (0);
2253 GNUNET_SCHEDULER_shutdown (); 2219 GNUNET_SCHEDULER_shutdown ();
2254 return; 2220 return;
2255 } 2221 }
2256 GNUNET_SERVER_add_handlers (server, handlers);
2257 GNUNET_SERVER_disconnect_notify (server, &handle_client_disconnect, NULL);
2258 GNUNET_SCHEDULER_add_shutdown (&cleanup_task, 2222 GNUNET_SCHEDULER_add_shutdown (&cleanup_task,
2259 NULL); 2223 NULL);
2260} 2224}
2261 2225
2262 2226
2263/** 2227/**
2264 * The main function for the template service. 2228 * Callback called when a client connects to the service.
2265 * 2229 *
2266 * @param argc number of arguments from the command line 2230 * @param cls closure for the service
2267 * @param argv command line arguments 2231 * @param c the new client that connected to the service
2268 * @return 0 ok, 1 on error 2232 * @param mq the message queue used to send messages to the client
2233 * @return @a c
2269 */ 2234 */
2270int 2235static void *
2271main (int argc, char *const *argv) 2236client_connect_cb (void *cls,
2237 struct GNUNET_SERVICE_Client *c,
2238 struct GNUNET_MQ_Handle *mq)
2272{ 2239{
2273 return (GNUNET_OK == 2240 struct ClientState *cs = GNUNET_new (struct ClientState);;
2274 GNUNET_SERVICE_run (argc, argv, "secretsharing", 2241
2275 GNUNET_SERVICE_OPTION_NONE, &run, NULL)) ? 0 : 1; 2242 cs->client = c;
2243 cs->mq = mq;
2244 return cs;
2276} 2245}
2246
2247
2248/**
2249 * Callback called when a client disconnected from the service
2250 *
2251 * @param cls closure for the service
2252 * @param c the client that disconnected
2253 * @param internal_cls should be equal to @a c
2254 */
2255static void
2256client_disconnect_cb (void *cls,
2257 struct GNUNET_SERVICE_Client *c,
2258 void *internal_cls)
2259{
2260 struct ClientState *cs = internal_cls;
2261
2262 if (NULL != cs->keygen_session)
2263 keygen_session_destroy (cs->keygen_session);
2264
2265 if (NULL != cs->decrypt_session)
2266 decrypt_session_destroy (cs->decrypt_session);
2267 GNUNET_free (cs);
2268}
2269
2270
2271/**
2272 * Define "main" method using service macro.
2273 */
2274GNUNET_SERVICE_MAIN
2275("secretsharing",
2276 GNUNET_SERVICE_OPTION_NONE,
2277 &run,
2278 &client_connect_cb,
2279 &client_disconnect_cb,
2280 NULL,
2281 GNUNET_MQ_hd_var_size (client_keygen,
2282 GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE,
2283 struct GNUNET_SECRETSHARING_CreateMessage,
2284 NULL),
2285 GNUNET_MQ_hd_var_size (client_decrypt,
2286 GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT,
2287 struct GNUNET_SECRETSHARING_DecryptRequestMessage,
2288 NULL),
2289 GNUNET_MQ_handler_end ());