GNUnet  0.10.x
Data Structures | Macros | Functions | Variables
gnunet-service-secretsharing.c File Reference

secret sharing service More...

#include "platform.h"
#include "gnunet_util_lib.h"
#include "gnunet_time_lib.h"
#include "gnunet_signatures.h"
#include "gnunet_consensus_service.h"
#include "secretsharing.h"
#include "secretsharing_protocol.h"
#include <gcrypt.h>
Include dependency graph for gnunet-service-secretsharing.c:

Go to the source code of this file.

Data Structures

struct  KeygenPeerInfo
 Info about a peer in a key generation session. More...
 
struct  DecryptPeerInfo
 Information about a peer in a decrypt session. More...
 
struct  KeygenSession
 Session to establish a threshold-shared secret. More...
 
struct  DecryptSession
 Session to cooperatively decrypt a value. More...
 
struct  ClientState
 State we keep per client. More...
 

Macros

#define EXTRA_CHECKS   1
 

Functions

static struct KeygenPeerInfoget_keygen_peer_info (const struct KeygenSession *ks, const struct GNUNET_PeerIdentity *peer)
 Get the peer info belonging to a peer identity in a keygen session. More...
 
static struct DecryptPeerInfoget_decrypt_peer_info (const struct DecryptSession *ds, const struct GNUNET_PeerIdentity *peer)
 Get the peer info belonging to a peer identity in a decrypt session. More...
 
static struct GNUNET_TIME_Absolute time_between (struct GNUNET_TIME_Absolute start, struct GNUNET_TIME_Absolute end, int num, int denum)
 Interpolate between two points in time. More...
 
static int peer_id_cmp (const void *p1, const void *p2)
 Compare two peer identities. More...
 
static int peer_find (const struct GNUNET_PeerIdentity *haystack, unsigned int n, const struct GNUNET_PeerIdentity *needle)
 Get the index of a peer in an array of peers. More...
 
static struct GNUNET_PeerIdentitynormalize_peers (struct GNUNET_PeerIdentity *listed, unsigned int num_listed, unsigned int *num_normalized, unsigned int *my_peer_idx)
 Normalize the given list of peers, by including the local peer (if it is missing) and sorting the peers by their identity. More...
 
static void compute_lagrange_coefficient (gcry_mpi_t coeff, unsigned int j, unsigned int *indices, unsigned int num)
 Get a the j-th lagrange coefficient for a set of indices. More...
 
static void decrypt_session_destroy (struct DecryptSession *ds)
 Destroy a decrypt session, removing it from the linked list of decrypt sessions. More...
 
static void keygen_info_destroy (struct KeygenPeerInfo *info)
 
static void keygen_session_destroy (struct KeygenSession *ks)
 
static void cleanup_task (void *cls)
 Task run during shutdown. More...
 
static void generate_presecret_polynomial (struct KeygenSession *ks)
 Generate the random coefficients of our pre-secret polynomial. More...
 
static void keygen_round1_new_element (void *cls, const struct GNUNET_SET_Element *element)
 Consensus element handler for round one. More...
 
static void horner_eval (gcry_mpi_t z, gcry_mpi_t *coeff, unsigned int num_coeff, gcry_mpi_t x, gcry_mpi_t m)
 Evaluate the polynomial with coefficients coeff at x. More...
 
static void keygen_round2_conclude (void *cls)
 
static void restore_fair (const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, const struct GNUNET_SECRETSHARING_FairEncryption *fe, gcry_mpi_t x, gcry_mpi_t xres)
 
static void get_fair_encryption_challenge (const struct GNUNET_SECRETSHARING_FairEncryption *fe, gcry_mpi_t *e)
 
static int verify_fair (const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, const struct GNUNET_SECRETSHARING_FairEncryption *fe)
 
static void encrypt_fair (gcry_mpi_t v, const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, struct GNUNET_SECRETSHARING_FairEncryption *fe)
 Create a fair Paillier encryption of then given ciphertext. More...
 
static void insert_round2_element (struct KeygenSession *ks)
 Insert round 2 element in the consensus, consisting of (1) The exponentiated pre-share polynomial coefficients A_{i,l}=g^{a_{i,l}} (2) The exponentiated pre-shares y_{i,j}=g^{s_{i,j}} (3) The encrypted pre-shares Y_{i,j} (4) The zero knowledge proof for fairness of the encryption. More...
 
static gcry_mpi_t keygen_reveal_get_exp_coeff (struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
 
static struct GNUNET_SECRETSHARING_FairEncryptionkeygen_reveal_get_enc_preshare (struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
 
static gcry_mpi_t keygen_reveal_get_exp_preshare (struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
 
static void keygen_round2_new_element (void *cls, const struct GNUNET_SET_Element *element)
 
static void keygen_round1_conclude (void *cls)
 Called when the first consensus round has concluded. More...
 
static void insert_round1_element (struct KeygenSession *ks)
 Insert the ephemeral key and the presecret commitment of this peer in the consensus of the given session. More...
 
static int check_client_keygen (void *cls, const struct GNUNET_SECRETSHARING_CreateMessage *msg)
 Check that msg is well-formed. More...
 
static void handle_client_keygen (void *cls, const struct GNUNET_SECRETSHARING_CreateMessage *msg)
 Functions with this signature are called whenever a message is received. More...
 
static void decrypt_conclude (void *cls)
 Called when the partial decryption consensus concludes. More...
 
static char * mpi_to_str (gcry_mpi_t mpi)
 Get a string representation of an MPI. More...
 
static void decrypt_new_element (void *cls, const struct GNUNET_SET_Element *element)
 Called when a new partial decryption arrives. More...
 
static void insert_decrypt_element (struct DecryptSession *ds)
 
static int check_client_decrypt (void *cls, const struct GNUNET_SECRETSHARING_DecryptRequestMessage *msg)
 Check that msg is well-formed. More...
 
static void handle_client_decrypt (void *cls, const struct GNUNET_SECRETSHARING_DecryptRequestMessage *msg)
 Functions with this signature are called whenever a message is received. More...
 
static void init_crypto_constants (void)
 
static void run (void *cls, const struct GNUNET_CONFIGURATION_Handle *c, struct GNUNET_SERVICE_Handle *service)
 Initialize secretsharing service. More...
 
static void * client_connect_cb (void *cls, struct GNUNET_SERVICE_Client *c, struct GNUNET_MQ_Handle *mq)
 Callback called when a client connects to the service. More...
 
static void client_disconnect_cb (void *cls, struct GNUNET_SERVICE_Client *c, void *internal_cls)
 Callback called when a client disconnected from the service. More...
 
 GNUNET_SERVICE_MAIN ("secretsharing", GNUNET_SERVICE_OPTION_NONE, &run, &client_connect_cb, &client_disconnect_cb, NULL, GNUNET_MQ_hd_var_size(client_keygen, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE, struct GNUNET_SECRETSHARING_CreateMessage, NULL), GNUNET_MQ_hd_var_size(client_decrypt, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT, struct GNUNET_SECRETSHARING_DecryptRequestMessage, NULL), GNUNET_MQ_handler_end())
 Define "main" method using service macro. More...
 

Variables

static gcry_mpi_t elgamal_q
 The ElGamal prime field order as libgcrypt mpi. More...
 
static gcry_mpi_t elgamal_p
 Modulus of the prime field used for ElGamal. More...
 
static gcry_mpi_t elgamal_g
 Generator for prime field of order 'elgamal_q'. More...
 
static struct GNUNET_PeerIdentity my_peer
 Peer that runs this service. More...
 
static struct GNUNET_CRYPTO_EddsaPrivateKeymy_peer_private_key
 Peer that runs this service. More...
 
static const struct GNUNET_CONFIGURATION_Handlecfg
 Configuration of this service. More...
 

Detailed Description

secret sharing service

Author
Florian Dold

Definition in file gnunet-service-secretsharing.c.

Macro Definition Documentation

◆ EXTRA_CHECKS

#define EXTRA_CHECKS   1

Definition at line 36 of file gnunet-service-secretsharing.c.

Function Documentation

◆ get_keygen_peer_info()

static struct KeygenPeerInfo* get_keygen_peer_info ( const struct KeygenSession ks,
const struct GNUNET_PeerIdentity peer 
)
static

Get the peer info belonging to a peer identity in a keygen session.

Parameters
ksThe keygen session.
peerThe peer identity.
Returns
The Keygen peer info, or NULL if the peer could not be found.

Definition at line 320 of file gnunet-service-secretsharing.c.

References GNUNET_memcmp, KeygenSession::info, KeygenSession::num_peers, and KeygenPeerInfo::peer.

Referenced by keygen_round1_new_element(), and keygen_round2_new_element().

322 {
323  unsigned int i;
324 
325  for (i = 0; i < ks->num_peers; i++)
326  if (0 == GNUNET_memcmp(peer, &ks->info[i].peer))
327  return &ks->info[i];
328  return NULL;
329 }
unsigned int num_peers
Total number of peers.
struct KeygenPeerInfo * info
Information about all participating peers.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
struct GNUNET_PeerIdentity peer
Peer identity of the peer.
Here is the caller graph for this function:

◆ get_decrypt_peer_info()

static struct DecryptPeerInfo* get_decrypt_peer_info ( const struct DecryptSession ds,
const struct GNUNET_PeerIdentity peer 
)
static

Get the peer info belonging to a peer identity in a decrypt session.

Parameters
dsThe decrypt session.
peerThe peer identity.
Returns
The decrypt peer info, or NULL if the peer could not be found.

Definition at line 340 of file gnunet-service-secretsharing.c.

References GNUNET_memcmp, DecryptSession::info, GNUNET_SECRETSHARING_Share::num_peers, DecryptPeerInfo::peer, and DecryptSession::share.

Referenced by decrypt_new_element().

342 {
343  unsigned int i;
344 
345  for (i = 0; i < ds->share->num_peers; i++)
346  if (0 == GNUNET_memcmp(peer, &ds->info[i].peer))
347  return &ds->info[i];
348  return NULL;
349 }
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
struct GNUNET_PeerIdentity peer
Identity of the peer.
struct DecryptPeerInfo * info
State information about other peers.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
uint16_t num_peers
Peers that have the share.
Here is the caller graph for this function:

◆ time_between()

static struct GNUNET_TIME_Absolute time_between ( struct GNUNET_TIME_Absolute  start,
struct GNUNET_TIME_Absolute  end,
int  num,
int  denum 
)
static

Interpolate between two points in time.

Parameters
startstart time
endend time
numnumerator of the scale factor
denumdenumerator of the scale factor

Definition at line 361 of file gnunet-service-secretsharing.c.

References GNUNET_TIME_Absolute::abs_value_us, end, GNUNET_assert, result, and start.

Referenced by keygen_round1_conclude().

364 {
366  uint64_t diff;
367 
369  diff = end.abs_value_us - start.abs_value_us;
370  result.abs_value_us = start.abs_value_us + ((diff * num) / denum);
371 
372  return result;
373 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
uint64_t abs_value_us
The actual value.
static int result
Global testing status.
Time for absolute times used by GNUnet, in microseconds.
Here is the caller graph for this function:

◆ peer_id_cmp()

static int peer_id_cmp ( const void *  p1,
const void *  p2 
)
static

Compare two peer identities.

Indended to be used with qsort or bsearch.

Parameters
p1Some peer identity.
p2Some peer identity.
Returns
1 if p1 > p2, -1 if p1 < p2 and 0 if p1 == p2.

Definition at line 384 of file gnunet-service-secretsharing.c.

Referenced by normalize_peers().

385 {
386  return memcmp(p1,
387  p2,
388  sizeof(struct GNUNET_PeerIdentity));
389 }
The identity of the host (wraps the signing key of the peer).
Here is the caller graph for this function:

◆ peer_find()

static int peer_find ( const struct GNUNET_PeerIdentity haystack,
unsigned int  n,
const struct GNUNET_PeerIdentity needle 
)
static

Get the index of a peer in an array of peers.

Parameters
haystackArray of peers.
nSize of haystack.
needlePeer to find
Returns
Index of needle in haystack, or -1 if peer is not in the list.

Definition at line 402 of file gnunet-service-secretsharing.c.

References GNUNET_memcmp.

Referenced by normalize_peers().

404 {
405  unsigned int i;
406 
407  for (i = 0; i < n; i++)
408  if (0 == GNUNET_memcmp(&haystack[i],
409  needle))
410  return i;
411  return -1;
412 }
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
Here is the caller graph for this function:

◆ normalize_peers()

static struct GNUNET_PeerIdentity* normalize_peers ( struct GNUNET_PeerIdentity listed,
unsigned int  num_listed,
unsigned int *  num_normalized,
unsigned int *  my_peer_idx 
)
static

Normalize the given list of peers, by including the local peer (if it is missing) and sorting the peers by their identity.

Parameters
listedPeers in the unnormalized list.
num_listedPeers in the un-normalized list.
[out]num_normalizedNumber of peers in the normalized list.
[out]my_peer_idxIndex of the local peer in the normalized list.
Returns
Normalized list, must be free'd by the caller.

Definition at line 426 of file gnunet-service-secretsharing.c.

References GNUNET_memcpy, GNUNET_new_array, GNUNET_NO, GNUNET_YES, my_peer, peer_find(), and peer_id_cmp().

Referenced by handle_client_keygen().

430 {
431  unsigned int local_peer_in_list;
432  /* number of peers in the normalized list */
433  unsigned int n;
434  struct GNUNET_PeerIdentity *normalized;
435 
436  local_peer_in_list = GNUNET_YES;
437  n = num_listed;
438  if (peer_find(listed, num_listed, &my_peer) < 0)
439  {
440  local_peer_in_list = GNUNET_NO;
441  n += 1;
442  }
443 
444  normalized = GNUNET_new_array(n,
445  struct GNUNET_PeerIdentity);
446 
447  if (GNUNET_NO == local_peer_in_list)
448  normalized[n - 1] = my_peer;
449 
450  GNUNET_memcpy(normalized,
451  listed,
452  num_listed * sizeof(struct GNUNET_PeerIdentity));
453  qsort(normalized,
454  n,
455  sizeof(struct GNUNET_PeerIdentity),
456  &peer_id_cmp);
457 
458  if (NULL != my_peer_idx)
459  *my_peer_idx = peer_find(normalized, n, &my_peer);
460  if (NULL != num_normalized)
461  *num_normalized = n;
462 
463  return normalized;
464 }
static int peer_id_cmp(const void *p1, const void *p2)
Compare two peer identities.
static int peer_find(const struct GNUNET_PeerIdentity *haystack, unsigned int n, const struct GNUNET_PeerIdentity *needle)
Get the index of a peer in an array of peers.
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
#define GNUNET_NO
Definition: gnunet_common.h:78
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
The identity of the host (wraps the signing key of the peer).
#define GNUNET_YES
Definition: gnunet_common.h:77
Here is the call graph for this function:
Here is the caller graph for this function:

◆ compute_lagrange_coefficient()

static void compute_lagrange_coefficient ( gcry_mpi_t  coeff,
unsigned int  j,
unsigned int *  indices,
unsigned int  num 
)
static

Get a the j-th lagrange coefficient for a set of indices.

Parameters
[out]coeffthe lagrange coefficient
jlagrange coefficient we want to compute
indicesindices
numnumber of indices in indices

Definition at line 476 of file gnunet-service-secretsharing.c.

References elgamal_q, GNUNET_assert, and l.

Referenced by decrypt_conclude().

479 {
480  unsigned int i;
481  /* numerator */
482  gcry_mpi_t n;
483  /* denominator */
484  gcry_mpi_t d;
485  /* temp value for l-j */
486  gcry_mpi_t tmp;
487 
488  GNUNET_assert(0 != coeff);
489 
490  GNUNET_assert(0 != (n = gcry_mpi_new(0)));
491  GNUNET_assert(0 != (d = gcry_mpi_new(0)));
492  GNUNET_assert(0 != (tmp = gcry_mpi_new(0)));
493 
494  gcry_mpi_set_ui(n, 1);
495  gcry_mpi_set_ui(d, 1);
496 
497  for (i = 0; i < num; i++)
498  {
499  unsigned int l = indices[i];
500  if (l == j)
501  continue;
502  gcry_mpi_mul_ui(n, n, l + 1);
503  // d <- d * (l-j)
504  gcry_mpi_set_ui(tmp, l + 1);
505  gcry_mpi_sub_ui(tmp, tmp, j + 1);
506  gcry_mpi_mul(d, d, tmp);
507  }
508 
509  // gcry_mpi_invm does not like negative numbers ...
510  gcry_mpi_mod(d, d, elgamal_q);
511 
512  GNUNET_assert(gcry_mpi_cmp_ui(d, 0) > 0);
513 
514  // now we do the actual division, with everything mod q, as we
515  // are not operating on elements from <g>, but on exponents
516  GNUNET_assert(0 != gcry_mpi_invm(d, d, elgamal_q));
517 
518  gcry_mpi_mulm(coeff, n, d, elgamal_q);
519 
520  gcry_mpi_release(n);
521  gcry_mpi_release(d);
522  gcry_mpi_release(tmp);
523 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static struct LoggingHandle * l
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
Here is the caller graph for this function:

◆ decrypt_session_destroy()

static void decrypt_session_destroy ( struct DecryptSession ds)
static

Destroy a decrypt session, removing it from the linked list of decrypt sessions.

Parameters
dsdecrypt session to destroy

Definition at line 533 of file gnunet-service-secretsharing.c.

References DecryptSession::consensus, DecryptSession::cs, ClientState::decrypt_session, GNUNET_CONSENSUS_destroy(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_log, GNUNET_SECRETSHARING_share_destroy(), DecryptSession::info, GNUNET_SECRETSHARING_Share::num_peers, DecryptPeerInfo::partial_decryption, and DecryptSession::share.

Referenced by client_disconnect_cb().

534 {
536  "destroying decrypt session\n");
537  if (NULL != ds->cs)
538  {
539  ds->cs->decrypt_session = NULL;
540  ds->cs = NULL;
541  }
542  if (NULL != ds->consensus)
543  {
545  ds->consensus = NULL;
546  }
547 
548  if (NULL != ds->info)
549  {
550  for (unsigned int i = 0; i < ds->share->num_peers; i++)
551  {
552  if (NULL != ds->info[i].partial_decryption)
553  {
554  gcry_mpi_release(ds->info[i].partial_decryption);
555  ds->info[i].partial_decryption = NULL;
556  }
557  }
558  GNUNET_free(ds->info);
559  ds->info = NULL;
560  }
561  if (NULL != ds->share)
562  {
564  ds->share = NULL;
565  }
566 
567  GNUNET_free(ds);
568 }
void GNUNET_CONSENSUS_destroy(struct GNUNET_CONSENSUS_Handle *consensus)
Destroy a consensus handle (free all state associated with it, no longer call any of the callbacks)...
void GNUNET_SECRETSHARING_share_destroy(struct GNUNET_SECRETSHARING_Share *share)
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
gcry_mpi_t partial_decryption
Set to the partial decryption of this peer, or NULL if we did not receive a partial decryption from t...
struct DecryptSession * decrypt_session
Decrypt session of the client, if any.
struct DecryptPeerInfo * info
State information about other peers.
struct ClientState * cs
Which client is this for?
struct GNUNET_CONSENSUS_Handle * consensus
Handle to the consensus over partial decryptions.
#define GNUNET_log(kind,...)
uint16_t num_peers
Peers that have the share.
#define GNUNET_free(ptr)
Wrapper around free.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ keygen_info_destroy()

static void keygen_info_destroy ( struct KeygenPeerInfo info)
static

Definition at line 572 of file gnunet-service-secretsharing.c.

References KeygenPeerInfo::presecret_commitment, KeygenPeerInfo::preshare_commitment, and KeygenPeerInfo::sigma.

Referenced by keygen_session_destroy().

573 {
574  if (NULL != info->sigma)
575  {
576  gcry_mpi_release(info->sigma);
577  info->sigma = NULL;
578  }
579  if (NULL != info->presecret_commitment)
580  {
581  gcry_mpi_release(info->presecret_commitment);
582  info->presecret_commitment = NULL;
583  }
584  if (NULL != info->preshare_commitment)
585  {
586  gcry_mpi_release(info->preshare_commitment);
587  info->preshare_commitment = NULL;
588  }
589 }
gcry_mpi_t preshare_commitment
Commitment to the preshare that is intended for our peer.
gcry_mpi_t presecret_commitment
The peer&#39;s commitment to its presecret.
gcry_mpi_t sigma
Sigma (exponentiated share) for this peer.
Here is the caller graph for this function:

◆ keygen_session_destroy()

static void keygen_session_destroy ( struct KeygenSession ks)
static

Definition at line 593 of file gnunet-service-secretsharing.c.

References KeygenSession::consensus, KeygenSession::cs, GNUNET_assert, GNUNET_CONSENSUS_destroy(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_log, KeygenSession::info, keygen_info_destroy(), ClientState::keygen_session, KeygenSession::my_share, KeygenSession::num_peers, KeygenSession::peers, KeygenSession::presecret_polynomial, KeygenSession::public_key, and KeygenSession::threshold.

Referenced by client_disconnect_cb().

594 {
596  "destroying keygen session\n");
597 
598  if (NULL != ks->cs)
599  {
600  ks->cs->keygen_session = NULL;
601  ks->cs = NULL;
602  }
603  if (NULL != ks->info)
604  {
605  for (unsigned int i = 0; i < ks->num_peers; i++)
606  keygen_info_destroy(&ks->info[i]);
607  GNUNET_free(ks->info);
608  ks->info = NULL;
609  }
610 
611  if (NULL != ks->consensus)
612  {
614  ks->consensus = NULL;
615  }
616 
617  if (NULL != ks->presecret_polynomial)
618  {
619  for (unsigned int i = 0; i < ks->threshold; i++)
620  {
621  GNUNET_assert(NULL != ks->presecret_polynomial[i]);
622  gcry_mpi_release(ks->presecret_polynomial[i]);
623  ks->presecret_polynomial[i] = NULL;
624  }
626  ks->presecret_polynomial = NULL;
627  }
628  if (NULL != ks->my_share)
629  {
630  gcry_mpi_release(ks->my_share);
631  ks->my_share = NULL;
632  }
633  if (NULL != ks->public_key)
634  {
635  gcry_mpi_release(ks->public_key);
636  ks->public_key = NULL;
637  }
638  if (NULL != ks->peers)
639  {
640  GNUNET_free(ks->peers);
641  ks->peers = NULL;
642  }
643  GNUNET_free(ks);
644 }
void GNUNET_CONSENSUS_destroy(struct GNUNET_CONSENSUS_Handle *consensus)
Destroy a consensus handle (free all state associated with it, no longer call any of the callbacks)...
static void keygen_info_destroy(struct KeygenPeerInfo *info)
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
gcry_mpi_t my_share
Share of our peer.
unsigned int threshold
Minimum number of shares required to restore the secret.
gcry_mpi_t public_key
Public key, will be updated when a round2 element arrives.
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
unsigned int num_peers
Total number of peers.
struct KeygenSession * keygen_session
Keygen session of the client, if any.
struct KeygenPeerInfo * info
Information about all participating peers.
gcry_mpi_t * presecret_polynomial
Randomly generated coefficients of the polynomial for sharing our pre-secret, where &#39;preshares[0]&#39; is...
struct GNUNET_PeerIdentity * peers
List of all peers involved in the secret sharing session.
#define GNUNET_log(kind,...)
struct ClientState * cs
Which client is this for?
#define GNUNET_free(ptr)
Wrapper around free.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ cleanup_task()

static void cleanup_task ( void *  cls)
static

Task run during shutdown.

Parameters
clsunused
tcunused

Definition at line 654 of file gnunet-service-secretsharing.c.

Referenced by run().

655 {
656  /* Nothing to do! */
657 }
Here is the caller graph for this function:

◆ generate_presecret_polynomial()

static void generate_presecret_polynomial ( struct KeygenSession ks)
static

Generate the random coefficients of our pre-secret polynomial.

Parameters
ksthe session

Definition at line 667 of file gnunet-service-secretsharing.c.

References elgamal_q, GNUNET_assert, GNUNET_new_array, GNUNET_SECRETSHARING_ELGAMAL_BITS, KeygenSession::presecret_polynomial, and KeygenSession::threshold.

Referenced by handle_client_keygen().

668 {
669  int i;
670  gcry_mpi_t v;
671 
672  GNUNET_assert(NULL == ks->presecret_polynomial);
674  gcry_mpi_t);
675  for (i = 0; i < ks->threshold; i++)
676  {
677  v = ks->presecret_polynomial[i] = gcry_mpi_new(GNUNET_SECRETSHARING_ELGAMAL_BITS);
678  GNUNET_assert(NULL != v);
679  // Randomize v such that 0 < v < elgamal_q.
680  // The '- 1' is necessary as bitlength(q) = bitlength(p) - 1.
681  do
682  {
683  gcry_mpi_randomize(v, GNUNET_SECRETSHARING_ELGAMAL_BITS - 1, GCRY_WEAK_RANDOM);
684  }
685  while ((gcry_mpi_cmp_ui(v, 0) == 0) || (gcry_mpi_cmp(v, elgamal_q) >= 0));
686  }
687 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
unsigned int threshold
Minimum number of shares required to restore the secret.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
gcry_mpi_t * presecret_polynomial
Randomly generated coefficients of the polynomial for sharing our pre-secret, where &#39;preshares[0]&#39; is...
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the caller graph for this function:

◆ keygen_round1_new_element()

static void keygen_round1_new_element ( void *  cls,
const struct GNUNET_SET_Element element 
)
static

Consensus element handler for round one.

We should get one ephemeral key for each peer.

Parameters
clsClosure (keygen session).
elementThe element from consensus, or NULL if consensus failed.

Definition at line 699 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_KeygenCommitData::commitment, GNUNET_SET_Element::data, get_keygen_peer_info(), GNUNET_CRYPTO_eddsa_verify(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_ERROR_TYPE_INFO, GNUNET_ERROR_TYPE_WARNING, GNUNET_i2s(), GNUNET_log, GNUNET_OK, GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG1, GNUNET_YES, KeygenPeerInfo::paillier_public_key, GNUNET_SECRETSHARING_KeygenCommitData::peer, KeygenPeerInfo::presecret_commitment, GNUNET_SECRETSHARING_KeygenCommitData::pubkey, GNUNET_PeerIdentity::public_key, GNUNET_SECRETSHARING_KeygenCommitData::purpose, KeygenPeerInfo::round1_valid, GNUNET_SECRETSHARING_KeygenCommitData::signature, GNUNET_CRYPTO_EccSignaturePurpose::size, and GNUNET_SET_Element::size.

Referenced by handle_client_keygen().

701 {
703  struct KeygenSession *ks = cls;
704  struct KeygenPeerInfo *info;
705 
706  if (NULL == element)
707  {
708  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "round1 consensus failed\n");
709  return;
710  }
711 
712  /* elements have fixed size */
713  if (element->size != sizeof(struct GNUNET_SECRETSHARING_KeygenCommitData))
714  {
716  "keygen commit data with wrong size (%u) in consensus, %u expected\n",
717  (unsigned int)element->size,
718  (unsigned int)sizeof(struct GNUNET_SECRETSHARING_KeygenCommitData));
719  return;
720  }
721 
722  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "got round1 element\n");
723 
724  d = element->data;
725  info = get_keygen_peer_info(ks, &d->peer);
726 
727  if (NULL == info)
728  {
729  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen commit data with wrong peer identity (%s) in consensus\n",
730  GNUNET_i2s(&d->peer));
731  return;
732  }
733 
734  /* Check that the right amount of data has been signed. */
735  if (d->purpose.size !=
736  htonl(element->size - offsetof(struct GNUNET_SECRETSHARING_KeygenCommitData, purpose)))
737  {
738  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen commit data with wrong signature purpose size in consensus\n");
739  return;
740  }
741 
743  &d->purpose, &d->signature, &d->peer.public_key))
744  {
745  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen commit data with invalid signature in consensus\n");
746  return;
747  }
748  info->paillier_public_key = d->pubkey;
750  info->round1_valid = GNUNET_YES;
751 }
struct GNUNET_CRYPTO_EddsaSignature signature
Signature over the rest of the message.
#define GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG1
Signature for the first round of distributed key generation.
struct GNUNET_PeerIdentity peer
Peer that inserts this element.
int round1_valid
Did we successfully receive the round1 element of the peer?
static struct KeygenPeerInfo * get_keygen_peer_info(const struct KeygenSession *ks, const struct GNUNET_PeerIdentity *peer)
Get the peer info belonging to a peer identity in a keygen session.
struct GNUNET_CRYPTO_PaillierPublicKey pubkey
Ephemeral paillier public key used by &#39;peer&#39; for this session.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
const void * data
Actual data of the element.
int GNUNET_CRYPTO_eddsa_verify(uint32_t purpose, const struct GNUNET_CRYPTO_EccSignaturePurpose *validate, const struct GNUNET_CRYPTO_EddsaSignature *sig, const struct GNUNET_CRYPTO_EddsaPublicKey *pub)
Verify EdDSA signature.
Definition: crypto_ecc.c:1116
Session to establish a threshold-shared secret.
gcry_mpi_t presecret_commitment
The peer&#39;s commitment to its presecret.
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!)...
struct GNUNET_HashCode commitment
Commitment of &#39;peer&#39; to its presecret.
struct GNUNET_CRYPTO_PaillierPublicKey paillier_public_key
The peer&#39;s paillier public key.
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
Signature purpose for signing the keygen commit data.
Info about a peer in a key generation session.
uint16_t size
Number of bytes in the buffer pointed to by data.
#define GNUNET_log(kind,...)
#define GNUNET_YES
Definition: gnunet_common.h:77
const char * GNUNET_i2s(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
Consensus element data used in the first round of key generation.
struct GNUNET_CRYPTO_EddsaPublicKey public_key
Here is the call graph for this function:
Here is the caller graph for this function:

◆ horner_eval()

static void horner_eval ( gcry_mpi_t  z,
gcry_mpi_t *  coeff,
unsigned int  num_coeff,
gcry_mpi_t  x,
gcry_mpi_t  m 
)
static

Evaluate the polynomial with coefficients coeff at x.

The i-th element in coeff corresponds to the coefficient of x^i.

Parameters
[out]zresult of the evaluation
coeffarray of coefficients
num_coeffnumber of coefficients
xwhere to evaluate the polynomial
mwhat group are we operating in?

Definition at line 765 of file gnunet-service-secretsharing.c.

Referenced by insert_round2_element().

766 {
767  unsigned int i;
768 
769  gcry_mpi_set_ui(z, 0);
770  for (i = 0; i < num_coeff; i++)
771  {
772  // z <- zx + c
773  gcry_mpi_mul(z, z, x);
774  gcry_mpi_addm(z, z, coeff[num_coeff - i - 1], m);
775  }
776 }
static struct GNUNET_ARM_MonitorHandle * m
Monitor connection with ARM.
Definition: gnunet-arm.c:99
Here is the caller graph for this function:

◆ keygen_round2_conclude()

static void keygen_round2_conclude ( void *  cls)
static

Definition at line 780 of file gnunet-service-secretsharing.c.

References KeygenSession::consensus, KeygenSession::cs, GNUNET_assert, GNUNET_CONSENSUS_destroy(), GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_INFO, GNUNET_log, GNUNET_memcmp, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_SECRET_READY, GNUNET_MQ_msg_extra, GNUNET_MQ_send(), GNUNET_new, GNUNET_new_array, GNUNET_OK, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SECRETSHARING_share_destroy(), GNUNET_SECRETSHARING_share_write(), GNUNET_YES, KeygenSession::info, KeygenSession::local_peer_idx, m, ClientState::mq, GNUNET_SECRETSHARING_Share::my_peer, my_peer, GNUNET_SECRETSHARING_Share::my_share, KeygenSession::my_share, KeygenSession::num_peers, GNUNET_SECRETSHARING_Share::num_peers, GNUNET_SECRETSHARING_Share::original_indices, KeygenPeerInfo::peer, GNUNET_SECRETSHARING_Share::peers, GNUNET_SECRETSHARING_Share::public_key, KeygenSession::public_key, KeygenPeerInfo::round2_valid, KeygenPeerInfo::sigma, and GNUNET_SECRETSHARING_Share::sigmas.

Referenced by keygen_round1_conclude().

781 {
782  struct KeygenSession *ks = cls;
784  struct GNUNET_MQ_Envelope *ev;
785  size_t share_size;
786  unsigned int i;
787  unsigned int j;
788  struct GNUNET_SECRETSHARING_Share *share;
789 
790  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "round2 conclude\n");
791 
793  ks->consensus = NULL;
794 
795  share = GNUNET_new(struct GNUNET_SECRETSHARING_Share);
796 
797  share->num_peers = 0;
798 
799  for (i = 0; i < ks->num_peers; i++)
800  if (GNUNET_YES == ks->info[i].round2_valid)
801  share->num_peers++;
802 
803  share->peers = GNUNET_new_array(share->num_peers,
804  struct GNUNET_PeerIdentity);
805  share->sigmas =
809  uint16_t);
810 
811  /* maybe we're not even in the list of peers? */
812  share->my_peer = share->num_peers;
813 
814  j = 0; /* running index of valid peers */
815  for (i = 0; i < ks->num_peers; i++)
816  {
817  if (GNUNET_YES == ks->info[i].round2_valid)
818  {
819  share->peers[j] = ks->info[i].peer;
822  ks->info[i].sigma);
823  share->original_indices[i] = j;
824  if (0 == GNUNET_memcmp(&share->peers[i], &my_peer))
825  share->my_peer = j;
826  j += 1;
827  }
828  }
829 
830  if (share->my_peer == share->num_peers)
831  {
832  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "P%u: peer identity not in share\n", ks->local_peer_idx);
833  }
834 
836  ks->my_share);
838  ks->public_key);
839 
840  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "keygen completed with %u peers\n", share->num_peers);
841 
842  /* Write the share. If 0 peers completed the dkg, an empty
843  * share will be sent. */
844 
845  GNUNET_assert(GNUNET_OK == GNUNET_SECRETSHARING_share_write(share, NULL, 0, &share_size));
846 
847  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "writing share of size %u\n",
848  (unsigned int)share_size);
849 
850  ev = GNUNET_MQ_msg_extra(m, share_size,
852 
853  GNUNET_assert(GNUNET_OK == GNUNET_SECRETSHARING_share_write(share, &m[1], share_size, NULL));
854 
856  share = NULL;
857 
858  GNUNET_MQ_send(ks->cs->mq,
859  ev);
860 }
void GNUNET_CONSENSUS_destroy(struct GNUNET_CONSENSUS_Handle *consensus)
Destroy a consensus handle (free all state associated with it, no longer call any of the callbacks)...
struct GNUNET_SECRETSHARING_FieldElement my_share
Share of &#39;my_peer&#39;.
struct GNUNET_MQ_Handle * mq
MQ to talk to client.
void GNUNET_SECRETSHARING_share_destroy(struct GNUNET_SECRETSHARING_Share *share)
struct GNUNET_PeerIdentity * peers
Peer identities (includes &#39;my_peer&#39;)
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
A share, with all values in in host byte order.
gcry_mpi_t my_share
Share of our peer.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
#define GNUNET_new(type)
Allocate a struct or union of the given type.
int round2_valid
Did we successfully receive the round2 element of the peer?
static struct GNUNET_ARM_MonitorHandle * m
Monitor connection with ARM.
Definition: gnunet-arm.c:99
gcry_mpi_t public_key
Public key, will be updated when a round2 element arrives.
#define GNUNET_MQ_msg_extra(mvar, esize, type)
Allocate an envelope, with extra space allocated after the space needed by the message struct...
Definition: gnunet_mq_lib.h:52
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
Session to establish a threshold-shared secret.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
int GNUNET_SECRETSHARING_share_write(const struct GNUNET_SECRETSHARING_Share *share, void *buf, size_t buflen, size_t *writelen)
Convert a share to its binary representation.
unsigned int local_peer_idx
Index of the local peer in the ordered list of peers in the session.
unsigned int num_peers
Total number of peers.
struct KeygenPeerInfo * info
Information about all participating peers.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
The identity of the host (wraps the signing key of the peer).
struct GNUNET_SECRETSHARING_FieldElement * sigmas
uint16_t my_peer
Index of our peer in the list.
#define GNUNET_log(kind,...)
struct GNUNET_PeerIdentity peer
Peer identity of the peer.
#define GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_SECRET_READY
The cryptosystem has been established.
#define GNUNET_YES
Definition: gnunet_common.h:77
void GNUNET_MQ_send(struct GNUNET_MQ_Handle *mq, struct GNUNET_MQ_Envelope *ev)
Send a message with the given message queue.
Definition: mq.c:351
gcry_mpi_t sigma
Sigma (exponentiated share) for this peer.
uint16_t num_peers
Peers that have the share.
struct GNUNET_SECRETSHARING_PublicKey public_key
Public key.
struct ClientState * cs
Which client is this for?
Notify the client that then threshold secret has been established.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ restore_fair()

static void restore_fair ( const struct GNUNET_CRYPTO_PaillierPublicKey ppub,
const struct GNUNET_SECRETSHARING_FairEncryption fe,
gcry_mpi_t  x,
gcry_mpi_t  xres 
)
static

Definition at line 865 of file gnunet-service-secretsharing.c.

References elgamal_q, GNUNET_assert, GNUNET_CRYPTO_mpi_scan_unsigned(), and t.

Referenced by keygen_round2_new_element().

868 {
869  gcry_mpi_t a_1;
870  gcry_mpi_t a_2;
871  gcry_mpi_t b_1;
872  gcry_mpi_t b_2;
873  gcry_mpi_t big_a;
874  gcry_mpi_t big_b;
875  gcry_mpi_t big_t;
876  gcry_mpi_t n;
877  gcry_mpi_t t_1;
878  gcry_mpi_t t_2;
879  gcry_mpi_t t;
880  gcry_mpi_t r;
881  gcry_mpi_t v;
882 
883 
884  GNUNET_assert(NULL != (n = gcry_mpi_new(0)));
885  GNUNET_assert(NULL != (t = gcry_mpi_new(0)));
886  GNUNET_assert(NULL != (t_1 = gcry_mpi_new(0)));
887  GNUNET_assert(NULL != (t_2 = gcry_mpi_new(0)));
888  GNUNET_assert(NULL != (r = gcry_mpi_new(0)));
889  GNUNET_assert(NULL != (big_t = gcry_mpi_new(0)));
890  GNUNET_assert(NULL != (v = gcry_mpi_new(0)));
891  GNUNET_assert(NULL != (big_a = gcry_mpi_new(0)));
892  GNUNET_assert(NULL != (big_b = gcry_mpi_new(0)));
893 
894  // a = (N,0)^T
896  ppub,
897  sizeof(struct GNUNET_CRYPTO_PaillierPublicKey));
898  GNUNET_assert(NULL != (a_2 = gcry_mpi_new(0)));
899  gcry_mpi_set_ui(a_2, 0);
900  // b = (x,1)^T
901  GNUNET_assert(NULL != (b_1 = gcry_mpi_new(0)));
902  gcry_mpi_set(b_1, x);
903  GNUNET_assert(NULL != (b_2 = gcry_mpi_new(0)));
904  gcry_mpi_set_ui(b_2, 1);
905 
906  // A = a DOT a
907  gcry_mpi_mul(t, a_1, a_1);
908  gcry_mpi_mul(big_a, a_2, a_2);
909  gcry_mpi_add(big_a, big_a, t);
910 
911  // B = b DOT b
912  gcry_mpi_mul(t, b_1, b_1);
913  gcry_mpi_mul(big_b, b_2, b_2);
914  gcry_mpi_add(big_b, big_b, t);
915 
916  while (1)
917  {
918  // n = a DOT b
919  gcry_mpi_mul(t, a_1, b_1);
920  gcry_mpi_mul(n, a_2, b_2);
921  gcry_mpi_add(n, n, t);
922 
923  // r = nearest(n/B)
924  gcry_mpi_div(r, NULL, n, big_b, 0);
925 
926  // T := A - 2rn + rrB
927  gcry_mpi_mul(v, r, n);
928  gcry_mpi_mul_ui(v, v, 2);
929  gcry_mpi_sub(big_t, big_a, v);
930  gcry_mpi_mul(v, r, r);
931  gcry_mpi_mul(v, v, big_b);
932  gcry_mpi_add(big_t, big_t, v);
933 
934  if (gcry_mpi_cmp(big_t, big_b) >= 0)
935  {
936  break;
937  }
938 
939  // t = a - rb
940  gcry_mpi_mul(v, r, b_1);
941  gcry_mpi_sub(t_1, a_1, v);
942  gcry_mpi_mul(v, r, b_2);
943  gcry_mpi_sub(t_2, a_2, v);
944 
945  // a = b
946  gcry_mpi_set(a_1, b_1);
947  gcry_mpi_set(a_2, b_2);
948  // b = t
949  gcry_mpi_set(b_1, t_1);
950  gcry_mpi_set(b_2, t_2);
951 
952  gcry_mpi_set(big_a, big_b);
953  gcry_mpi_set(big_b, big_t);
954  }
955 
956  gcry_mpi_set(xres, b_2);
957  gcry_mpi_invm(xres, xres, elgamal_q);
958  gcry_mpi_mulm(xres, xres, b_1, elgamal_q);
959 
960  gcry_mpi_release(a_1);
961  gcry_mpi_release(a_2);
962  gcry_mpi_release(b_1);
963  gcry_mpi_release(b_2);
964  gcry_mpi_release(big_a);
965  gcry_mpi_release(big_b);
966  gcry_mpi_release(big_t);
967  gcry_mpi_release(n);
968  gcry_mpi_release(t_1);
969  gcry_mpi_release(t_2);
970  gcry_mpi_release(t);
971  gcry_mpi_release(r);
972  gcry_mpi_release(v);
973 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static struct GNUNET_SCHEDULER_Task * t
Main task.
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_fair_encryption_challenge()

static void get_fair_encryption_challenge ( const struct GNUNET_SECRETSHARING_FairEncryption fe,
gcry_mpi_t *  e 
)
static

Definition at line 977 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_FairEncryption::c, elgamal_q, GNUNET_CRYPTO_hash(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_CRYPTO_PAILLIER_BITS, GNUNET_memcpy, GNUNET_SECRETSHARING_ELGAMAL_BITS, h, GNUNET_SECRETSHARING_FairEncryption::h, GNUNET_SECRETSHARING_FairEncryption::t1, and GNUNET_SECRETSHARING_FairEncryption::t2.

Referenced by encrypt_fair(), and verify_fair().

979 {
980  struct {
984  char t2[GNUNET_CRYPTO_PAILLIER_BITS * 2 / 8];
985  } hash_data;
986  struct GNUNET_HashCode e_hash;
987 
988  memset(&hash_data,
989  0,
990  sizeof(hash_data));
991  GNUNET_memcpy(&hash_data.c, &fe->c, sizeof(struct GNUNET_CRYPTO_PaillierCiphertext));
992  GNUNET_memcpy(&hash_data.h, &fe->h, GNUNET_SECRETSHARING_ELGAMAL_BITS / 8);
993  GNUNET_memcpy(&hash_data.t1, &fe->t1, GNUNET_SECRETSHARING_ELGAMAL_BITS / 8);
994  GNUNET_memcpy(&hash_data.t2, &fe->t2, GNUNET_CRYPTO_PAILLIER_BITS * 2 / 8);
995  GNUNET_CRYPTO_hash(&hash_data,
996  sizeof(hash_data),
997  &e_hash);
998  /* This allocates "e" */
1000  &e_hash,
1001  sizeof(struct GNUNET_HashCode));
1002  gcry_mpi_mod(*e, *e, elgamal_q);
1003 }
char h[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
h = g^x, where x is the fairly encrypte secret.
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
static struct Experiment * e
char t1[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
static struct GNUNET_ARM_Handle * h
Connection with ARM.
Definition: gnunet-arm.c:94
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:44
A 512-bit hashcode.
char t2[GNUNET_CRYPTO_PAILLIER_BITS *2/8]
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
#define GNUNET_CRYPTO_PAILLIER_BITS
Size of paillier plain texts and public keys.
struct GNUNET_CRYPTO_PaillierCiphertext c
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ verify_fair()

static int verify_fair ( const struct GNUNET_CRYPTO_PaillierPublicKey ppub,
const struct GNUNET_SECRETSHARING_FairEncryption fe 
)
static

Definition at line 1007 of file gnunet-service-secretsharing.c.

References GNUNET_CRYPTO_PaillierCiphertext::bits, GNUNET_SECRETSHARING_FairEncryption::c, cleanup(), e, elgamal_g, elgamal_p, get_fair_encryption_challenge(), GNUNET_assert, GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_CRYPTO_PAILLIER_BITS, GNUNET_ERROR_TYPE_ERROR, GNUNET_log, GNUNET_NO, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_YES, GNUNET_SECRETSHARING_FairEncryption::h, res, GNUNET_SECRETSHARING_FairEncryption::t1, GNUNET_SECRETSHARING_FairEncryption::t2, GNUNET_SECRETSHARING_FairEncryption::w, and GNUNET_SECRETSHARING_FairEncryption::z.

Referenced by keygen_round2_new_element().

1009 {
1010  gcry_mpi_t n;
1011  gcry_mpi_t n_sq;
1012  gcry_mpi_t z;
1013  gcry_mpi_t t1;
1014  gcry_mpi_t t2;
1015  gcry_mpi_t e;
1016  gcry_mpi_t w;
1017  gcry_mpi_t tmp1;
1018  gcry_mpi_t tmp2;
1019  gcry_mpi_t y;
1020  gcry_mpi_t big_y;
1021  int res;
1022 
1023  GNUNET_assert(NULL != (n_sq = gcry_mpi_new(0)));
1024  GNUNET_assert(NULL != (tmp1 = gcry_mpi_new(0)));
1025  GNUNET_assert(NULL != (tmp2 = gcry_mpi_new(0)));
1026 
1028  &e /* this allocates e */);
1029 
1031  ppub,
1032  sizeof(struct GNUNET_CRYPTO_PaillierPublicKey));
1039  gcry_mpi_mul(n_sq, n, n);
1040 
1041  // tmp1 = g^z
1042  gcry_mpi_powm(tmp1, elgamal_g, z, elgamal_p);
1043  // tmp2 = y^{-e}
1044  gcry_mpi_powm(tmp1, y, e, elgamal_p);
1045  gcry_mpi_invm(tmp1, tmp1, elgamal_p);
1046  // tmp1 = tmp1 * tmp2
1047  gcry_mpi_mulm(tmp1, tmp1, tmp2, elgamal_p);
1048 
1049  if (0 == gcry_mpi_cmp(t1, tmp1))
1050  {
1051  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "fair encryption invalid (t1)\n");
1052  res = GNUNET_NO;
1053  goto cleanup;
1054  }
1055 
1056  gcry_mpi_powm(big_y, big_y, e, n_sq);
1057  gcry_mpi_invm(big_y, big_y, n_sq);
1058 
1059  gcry_mpi_add_ui(tmp1, n, 1);
1060  gcry_mpi_powm(tmp1, tmp1, z, n_sq);
1061 
1062  gcry_mpi_powm(tmp2, w, n, n_sq);
1063 
1064  gcry_mpi_mulm(tmp1, tmp1, tmp2, n_sq);
1065  gcry_mpi_mulm(tmp1, tmp1, big_y, n_sq);
1066 
1067 
1068  if (0 == gcry_mpi_cmp(t2, tmp1))
1069  {
1070  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "fair encryption invalid (t2)\n");
1071  res = GNUNET_NO;
1072  goto cleanup;
1073  }
1074 
1075  res = GNUNET_YES;
1076 
1077 cleanup:
1078 
1079  gcry_mpi_release(n);
1080  gcry_mpi_release(n_sq);
1081  gcry_mpi_release(z);
1082  gcry_mpi_release(t1);
1083  gcry_mpi_release(t2);
1084  gcry_mpi_release(e);
1085  gcry_mpi_release(w);
1086  gcry_mpi_release(tmp1);
1087  gcry_mpi_release(tmp2);
1088  gcry_mpi_release(y);
1089  gcry_mpi_release(big_y);
1090  return res;
1091 }
char h[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
h = g^x, where x is the fairly encrypte secret.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static struct Experiment * e
#define GNUNET_NO
Definition: gnunet_common.h:78
char t1[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
static void get_fair_encryption_challenge(const struct GNUNET_SECRETSHARING_FairEncryption *fe, gcry_mpi_t *e)
unsigned char bits[2048 *2/8]
The bits of the ciphertext.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static void cleanup(void *cls)
Function scheduled as very last function, cleans up after us.
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
char t2[GNUNET_CRYPTO_PAILLIER_BITS *2/8]
static int res
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
char z[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
#define GNUNET_log(kind,...)
#define GNUNET_YES
Definition: gnunet_common.h:77
char w[GNUNET_CRYPTO_PAILLIER_BITS/8]
#define GNUNET_CRYPTO_PAILLIER_BITS
Size of paillier plain texts and public keys.
struct GNUNET_CRYPTO_PaillierCiphertext c
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ encrypt_fair()

static void encrypt_fair ( gcry_mpi_t  v,
const struct GNUNET_CRYPTO_PaillierPublicKey ppub,
struct GNUNET_SECRETSHARING_FairEncryption fe 
)
static

Create a fair Paillier encryption of then given ciphertext.

Parameters
vthe ciphertext
[out]fethe fair encryption

Definition at line 1101 of file gnunet-service-secretsharing.c.

References GNUNET_CRYPTO_PaillierCiphertext::bits, GNUNET_SECRETSHARING_FairEncryption::c, e, elgamal_g, elgamal_p, elgamal_q, get_fair_encryption_challenge(), GNUNET_assert, GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_CRYPTO_PAILLIER_BITS, GNUNET_SECRETSHARING_ELGAMAL_BITS, h, GNUNET_SECRETSHARING_FairEncryption::h, GNUNET_SECRETSHARING_FairEncryption::t1, GNUNET_SECRETSHARING_FairEncryption::t2, GNUNET_SECRETSHARING_FairEncryption::w, and GNUNET_SECRETSHARING_FairEncryption::z.

Referenced by insert_round2_element().

1104 {
1105  gcry_mpi_t r;
1106  gcry_mpi_t s;
1107  gcry_mpi_t t1;
1108  gcry_mpi_t t2;
1109  gcry_mpi_t z;
1110  gcry_mpi_t w;
1111  gcry_mpi_t n;
1112  gcry_mpi_t e;
1113  gcry_mpi_t n_sq;
1114  gcry_mpi_t u;
1115  gcry_mpi_t Y;
1116  gcry_mpi_t G;
1117  gcry_mpi_t h;
1118 
1119  GNUNET_assert(NULL != (r = gcry_mpi_new(0)));
1120  GNUNET_assert(NULL != (s = gcry_mpi_new(0)));
1121  GNUNET_assert(NULL != (t1 = gcry_mpi_new(0)));
1122  GNUNET_assert(NULL != (t2 = gcry_mpi_new(0)));
1123  GNUNET_assert(NULL != (z = gcry_mpi_new(0)));
1124  GNUNET_assert(NULL != (w = gcry_mpi_new(0)));
1125  GNUNET_assert(NULL != (n_sq = gcry_mpi_new(0)));
1126  GNUNET_assert(NULL != (u = gcry_mpi_new(0)));
1127  GNUNET_assert(NULL != (Y = gcry_mpi_new(0)));
1128  GNUNET_assert(NULL != (G = gcry_mpi_new(0)));
1129  GNUNET_assert(NULL != (h = gcry_mpi_new(0)));
1130 
1132  ppub,
1133  sizeof(struct GNUNET_CRYPTO_PaillierPublicKey));
1134  gcry_mpi_mul(n_sq, n, n);
1135  gcry_mpi_add_ui(G, n, 1);
1136 
1137  do
1138  {
1139  gcry_mpi_randomize(u, GNUNET_CRYPTO_PAILLIER_BITS, GCRY_WEAK_RANDOM);
1140  }
1141  while (gcry_mpi_cmp(u, n) >= 0);
1142 
1143  gcry_mpi_powm(t1, G, v, n_sq);
1144  gcry_mpi_powm(t2, u, n, n_sq);
1145  gcry_mpi_mulm(Y, t1, t2, n_sq);
1146 
1148  sizeof fe->c.bits,
1149  Y);
1150 
1151 
1152  gcry_mpi_randomize(r, 2048, GCRY_WEAK_RANDOM);
1153  do
1154  {
1155  gcry_mpi_randomize(s, GNUNET_CRYPTO_PAILLIER_BITS, GCRY_WEAK_RANDOM);
1156  }
1157  while (gcry_mpi_cmp(s, n) >= 0);
1158 
1159  // compute t1
1160  gcry_mpi_mulm(t1, elgamal_g, r, elgamal_p);
1161  // compute t2 (use z and w as temp)
1162  gcry_mpi_powm(z, G, r, n_sq);
1163  gcry_mpi_powm(w, s, n, n_sq);
1164  gcry_mpi_mulm(t2, z, w, n_sq);
1165 
1166 
1167  gcry_mpi_powm(h, elgamal_g, v, elgamal_p);
1168 
1171  h);
1172 
1175  t1);
1176 
1179  t2);
1180 
1182  &e /* This allocates "e" */);
1183 
1184  // compute z
1185  gcry_mpi_mul(z, e, v);
1186  gcry_mpi_addm(z, z, r, elgamal_q);
1187  // compute w
1188  gcry_mpi_powm(w, u, e, n);
1189  gcry_mpi_mulm(w, w, s, n);
1190 
1193  z);
1194 
1197  w);
1198 
1199  gcry_mpi_release(n);
1200  gcry_mpi_release(r);
1201  gcry_mpi_release(s);
1202  gcry_mpi_release(t1);
1203  gcry_mpi_release(t2);
1204  gcry_mpi_release(z);
1205  gcry_mpi_release(w);
1206  gcry_mpi_release(e);
1207  gcry_mpi_release(n_sq);
1208  gcry_mpi_release(u);
1209  gcry_mpi_release(Y);
1210  gcry_mpi_release(G);
1211  gcry_mpi_release(h);
1212 }
char h[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
h = g^x, where x is the fairly encrypte secret.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
static struct Experiment * e
char t1[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
static struct GNUNET_ARM_Handle * h
Connection with ARM.
Definition: gnunet-arm.c:94
static void get_fair_encryption_challenge(const struct GNUNET_SECRETSHARING_FairEncryption *fe, gcry_mpi_t *e)
unsigned char bits[2048 *2/8]
The bits of the ciphertext.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
char t2[GNUNET_CRYPTO_PAILLIER_BITS *2/8]
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
char z[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
char w[GNUNET_CRYPTO_PAILLIER_BITS/8]
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
#define GNUNET_CRYPTO_PAILLIER_BITS
Size of paillier plain texts and public keys.
struct GNUNET_CRYPTO_PaillierCiphertext c
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ insert_round2_element()

static void insert_round2_element ( struct KeygenSession ks)
static

Insert round 2 element in the consensus, consisting of (1) The exponentiated pre-share polynomial coefficients A_{i,l}=g^{a_{i,l}} (2) The exponentiated pre-shares y_{i,j}=g^{s_{i,j}} (3) The encrypted pre-shares Y_{i,j} (4) The zero knowledge proof for fairness of the encryption.

Parameters
kssession to use

Definition at line 1226 of file gnunet-service-secretsharing.c.

References KeygenSession::consensus, GNUNET_SET_Element::data, element_size, elgamal_g, elgamal_p, elgamal_q, encrypt_fair(), GNUNET_assert, GNUNET_CONSENSUS_insert(), GNUNET_CRYPTO_eddsa_sign(), GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_log, GNUNET_malloc, GNUNET_OK, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG2, GNUNET_YES, horner_eval(), KeygenSession::info, KeygenSession::local_peer_idx, my_peer, KeygenSession::num_peers, KeygenPeerInfo::paillier_public_key, GNUNET_SECRETSHARING_KeygenRevealData::peer, KeygenSession::presecret_polynomial, GNUNET_SECRETSHARING_KeygenRevealData::purpose, GNUNET_CRYPTO_EccSignaturePurpose::purpose, KeygenPeerInfo::round1_valid, GNUNET_SECRETSHARING_KeygenRevealData::signature, GNUNET_CRYPTO_EccSignaturePurpose::size, GNUNET_SET_Element::size, and KeygenSession::threshold.

Referenced by keygen_round1_conclude().

1227 {
1228  struct GNUNET_SET_Element *element;
1230  unsigned char *pos;
1231  unsigned char *last_pos;
1232  size_t element_size;
1233  unsigned int i;
1234  gcry_mpi_t idx;
1235  gcry_mpi_t v;
1236 
1237  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "P%u: Inserting round2 element\n",
1238  ks->local_peer_idx);
1239 
1240  GNUNET_assert(NULL != (v = gcry_mpi_new(GNUNET_SECRETSHARING_ELGAMAL_BITS)));
1241  GNUNET_assert(NULL != (idx = gcry_mpi_new(GNUNET_SECRETSHARING_ELGAMAL_BITS)));
1242 
1243  element_size = (sizeof(struct GNUNET_SECRETSHARING_KeygenRevealData) +
1244  sizeof(struct GNUNET_SECRETSHARING_FairEncryption) * ks->num_peers +
1246 
1247  element = GNUNET_malloc(sizeof(struct GNUNET_SET_Element) + element_size);
1248  element->size = element_size;
1249  element->data = (void *)&element[1];
1250 
1251  d = (void *)element->data;
1252  d->peer = my_peer;
1253 
1254  // start inserting vector elements
1255  // after the fixed part of the element's data
1256  pos = (void *)&d[1];
1257  last_pos = pos + element_size;
1258 
1259  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "P%u: computed exp preshares\n",
1260  ks->local_peer_idx);
1261 
1262  // encrypted pre-shares
1263  // and fair encryption proof
1264  {
1265  for (i = 0; i < ks->num_peers; i++)
1266  {
1267  ptrdiff_t remaining = last_pos - pos;
1268  struct GNUNET_SECRETSHARING_FairEncryption *fe = (void *)pos;
1269 
1270  GNUNET_assert(remaining > 0);
1271  memset(fe, 0, sizeof *fe);
1272  if (GNUNET_YES == ks->info[i].round1_valid)
1273  {
1274  gcry_mpi_set_ui(idx, i + 1);
1275  // evaluate the polynomial
1277  // encrypt the result
1278  encrypt_fair(v, &ks->info[i].paillier_public_key, fe);
1279  }
1280  pos += sizeof *fe;
1281  }
1282  }
1283 
1284  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "P%u: computed enc preshares\n",
1285  ks->local_peer_idx);
1286 
1287  // exponentiated coefficients
1288  for (i = 0; i < ks->threshold; i++)
1289  {
1290  ptrdiff_t remaining = last_pos - pos;
1291  GNUNET_assert(remaining > 0);
1292  gcry_mpi_powm(v, elgamal_g, ks->presecret_polynomial[i], elgamal_p);
1295  }
1296 
1297  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "P%u: computed exp coefficients\n",
1298  ks->local_peer_idx);
1299 
1300 
1301  d->purpose.size = htonl(element_size - offsetof(struct GNUNET_SECRETSHARING_KeygenRevealData, purpose));
1305  &d->purpose,
1306  &d->signature));
1307 
1308  GNUNET_CONSENSUS_insert(ks->consensus, element, NULL, NULL);
1309  GNUNET_free(element); /* FIXME: maybe stack-allocate instead? */
1310 
1311  gcry_mpi_release(v);
1312  gcry_mpi_release(idx);
1313 }
static unsigned int element_size
int round1_valid
Did we successfully receive the round1 element of the peer?
uint32_t purpose
What does this signature vouch for? This must contain a GNUNET_SIGNATURE_PURPOSE_XXX constant (from g...
Element stored in a set.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
struct GNUNET_CRYPTO_EddsaSignature signature
Signature over rest of the message.
int GNUNET_CRYPTO_eddsa_sign(const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose, struct GNUNET_CRYPTO_EddsaSignature *sig)
EdDSA sign a given block.
Definition: crypto_ecc.c:989
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
unsigned int threshold
Minimum number of shares required to restore the secret.
void GNUNET_CONSENSUS_insert(struct GNUNET_CONSENSUS_Handle *consensus, const struct GNUNET_SET_Element *element, GNUNET_CONSENSUS_InsertDoneCallback idc, void *idc_cls)
Insert an element in the set being reconsiled.
const void * data
Actual data of the element.
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static struct GNUNET_CRYPTO_EddsaPrivateKey * my_peer_private_key
Peer that runs this service.
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!)...
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
unsigned int local_peer_idx
Index of the local peer in the ordered list of peers in the session.
struct GNUNET_CRYPTO_PaillierPublicKey paillier_public_key
The peer&#39;s paillier public key.
unsigned int num_peers
Total number of peers.
static void encrypt_fair(gcry_mpi_t v, const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, struct GNUNET_SECRETSHARING_FairEncryption *fe)
Create a fair Paillier encryption of then given ciphertext.
struct KeygenPeerInfo * info
Information about all participating peers.
struct GNUNET_PeerIdentity peer
Peer that inserts this element.
gcry_mpi_t * presecret_polynomial
Randomly generated coefficients of the polynomial for sharing our pre-secret, where &#39;preshares[0]&#39; is...
uint16_t size
Number of bytes in the buffer pointed to by data.
#define GNUNET_log(kind,...)
#define GNUNET_YES
Definition: gnunet_common.h:77
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
#define GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG2
Signature for the second round of distributed key generation.
static void horner_eval(gcry_mpi_t z, gcry_mpi_t *coeff, unsigned int num_coeff, gcry_mpi_t x, gcry_mpi_t m)
Evaluate the polynomial with coefficients coeff at x.
#define GNUNET_malloc(size)
Wrapper around malloc.
#define GNUNET_free(ptr)
Wrapper around free.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ keygen_reveal_get_exp_coeff()

static gcry_mpi_t keygen_reveal_get_exp_coeff ( struct KeygenSession ks,
const struct GNUNET_SECRETSHARING_KeygenRevealData d,
unsigned int  idx 
)
static

Definition at line 1317 of file gnunet-service-secretsharing.c.

References GNUNET_assert, GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_SECRETSHARING_ELGAMAL_BITS, KeygenSession::num_peers, and threshold.

Referenced by keygen_round2_new_element().

1320 {
1321  unsigned char *pos;
1322  gcry_mpi_t exp_coeff;
1323 
1324  GNUNET_assert(idx < ks->threshold);
1325 
1326  pos = (void *)&d[1];
1327  // skip encrypted pre-shares
1328  pos += sizeof(struct GNUNET_SECRETSHARING_FairEncryption) * ks->num_peers;
1329  // skip exp. coeffs we are not interested in
1330  pos += GNUNET_SECRETSHARING_ELGAMAL_BITS / 8 * idx;
1331  // the first exponentiated coefficient is the public key share
1333  return exp_coeff;
1334 }
static unsigned int threshold
What should the threshold for then key be?
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
unsigned int num_peers
Total number of peers.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ keygen_reveal_get_enc_preshare()

static struct GNUNET_SECRETSHARING_FairEncryption* keygen_reveal_get_enc_preshare ( struct KeygenSession ks,
const struct GNUNET_SECRETSHARING_KeygenRevealData d,
unsigned int  idx 
)
static

Definition at line 1338 of file gnunet-service-secretsharing.c.

References GNUNET_assert, and num_peers.

Referenced by keygen_reveal_get_exp_preshare(), and keygen_round2_new_element().

1341 {
1342  unsigned char *pos;
1343 
1344  GNUNET_assert(idx < ks->num_peers);
1345 
1346  pos = (void *)&d[1];
1347  // skip encrypted pre-shares we're not interested in
1348  pos += sizeof(struct GNUNET_SECRETSHARING_FairEncryption) * idx;
1349  return (struct GNUNET_SECRETSHARING_FairEncryption *)pos;
1350 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static unsigned int num_peers
Here is the caller graph for this function:

◆ keygen_reveal_get_exp_preshare()

static gcry_mpi_t keygen_reveal_get_exp_preshare ( struct KeygenSession ks,
const struct GNUNET_SECRETSHARING_KeygenRevealData d,
unsigned int  idx 
)
static

Definition at line 1354 of file gnunet-service-secretsharing.c.

References GNUNET_assert, GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SECRETSHARING_FairEncryption::h, keygen_reveal_get_enc_preshare(), and num_peers.

Referenced by keygen_round2_new_element().

1357 {
1358  gcry_mpi_t exp_preshare;
1360 
1361  GNUNET_assert(idx < ks->num_peers);
1362  fe = keygen_reveal_get_enc_preshare(ks, d, idx);
1364  return exp_preshare;
1365 }
char h[GNUNET_SECRETSHARING_ELGAMAL_BITS/8]
h = g^x, where x is the fairly encrypte secret.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
static struct GNUNET_SECRETSHARING_FairEncryption * keygen_reveal_get_enc_preshare(struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
static unsigned int num_peers
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ keygen_round2_new_element()

static void keygen_round2_new_element ( void *  cls,
const struct GNUNET_SET_Element element 
)
static

Definition at line 1369 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_FairEncryption::c, GNUNET_SET_Element::data, elgamal_g, elgamal_p, elgamal_q, get_keygen_peer_info(), GNUNET_assert, GNUNET_CRYPTO_eddsa_verify(), GNUNET_CRYPTO_paillier_decrypt(), GNUNET_ERROR_TYPE_INFO, GNUNET_ERROR_TYPE_WARNING, GNUNET_i2s(), GNUNET_log, GNUNET_NO, GNUNET_OK, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG2, GNUNET_YES, KeygenSession::info, keygen_reveal_get_enc_preshare(), keygen_reveal_get_exp_coeff(), keygen_reveal_get_exp_preshare(), KeygenSession::local_peer_idx, KeygenSession::my_share, KeygenSession::num_peers, KeygenSession::paillier_private_key, KeygenPeerInfo::paillier_public_key, GNUNET_SECRETSHARING_KeygenRevealData::peer, KeygenPeerInfo::preshare_commitment, GNUNET_PeerIdentity::public_key, KeygenSession::public_key, GNUNET_SECRETSHARING_KeygenRevealData::purpose, restore_fair(), KeygenPeerInfo::round1_valid, KeygenPeerInfo::round2_valid, KeygenPeerInfo::sigma, GNUNET_SECRETSHARING_KeygenRevealData::signature, GNUNET_CRYPTO_EccSignaturePurpose::size, GNUNET_SET_Element::size, KeygenSession::threshold, and verify_fair().

Referenced by keygen_round1_conclude().

1371 {
1372  struct KeygenSession *ks = cls;
1373  const struct GNUNET_SECRETSHARING_KeygenRevealData *d;
1374  struct KeygenPeerInfo *info;
1375  size_t expected_element_size;
1376  unsigned int j;
1377  int cmp_result;
1378  gcry_mpi_t tmp;
1379  gcry_mpi_t public_key_share;
1380  gcry_mpi_t preshare;
1381 
1382  if (NULL == element)
1383  {
1384  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "round2 consensus failed\n");
1385  return;
1386  }
1387 
1388  expected_element_size = (sizeof(struct GNUNET_SECRETSHARING_KeygenRevealData) +
1389  sizeof(struct GNUNET_SECRETSHARING_FairEncryption) * ks->num_peers +
1391 
1392  if (element->size != expected_element_size)
1393  {
1395  "keygen round2 data with wrong size (%u) in consensus, %u expected\n",
1396  (unsigned int)element->size,
1397  (unsigned int)expected_element_size);
1398  return;
1399  }
1400 
1401  d = (const void *)element->data;
1402 
1403  info = get_keygen_peer_info(ks, &d->peer);
1404 
1405  if (NULL == info)
1406  {
1407  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen commit data with wrong peer identity (%s) in consensus\n",
1408  GNUNET_i2s(&d->peer));
1409  return;
1410  }
1411 
1412  if (GNUNET_NO == info->round1_valid)
1413  {
1415  "ignoring round2 element from peer with invalid round1 element (%s)\n",
1416  GNUNET_i2s(&d->peer));
1417  return;
1418  }
1419 
1420  if (GNUNET_YES == info->round2_valid)
1421  {
1423  "ignoring duplicate round2 element (%s)\n",
1424  GNUNET_i2s(&d->peer));
1425  return;
1426  }
1427 
1428  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "got round2 element\n");
1429 
1430  if (ntohl(d->purpose.size) !=
1431  element->size - offsetof(struct GNUNET_SECRETSHARING_KeygenRevealData, purpose))
1432  {
1433  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen reveal data with wrong signature purpose size in consensus\n");
1434  return;
1435  }
1436 
1438  &d->purpose, &d->signature, &d->peer.public_key))
1439  {
1440  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "keygen reveal data with invalid signature in consensus\n");
1441  return;
1442  }
1443 
1444  public_key_share = keygen_reveal_get_exp_coeff(ks, d, 0);
1446 
1447  if (NULL == ks->public_key)
1448  {
1449  GNUNET_assert(NULL != (ks->public_key = gcry_mpi_new(0)));
1450  gcry_mpi_set_ui(ks->public_key, 1);
1451  }
1452  gcry_mpi_mulm(ks->public_key, ks->public_key, public_key_share, elgamal_p);
1453 
1454  gcry_mpi_release(public_key_share);
1455  public_key_share = NULL;
1456 
1457  {
1459  GNUNET_assert(NULL != (preshare = gcry_mpi_new(0)));
1462  &fe->c,
1463  preshare);
1464 
1465  // FIXME: not doing the restoration is less expensive
1467  fe,
1468  preshare,
1469  preshare);
1470  }
1471 
1472  GNUNET_assert(NULL != (tmp = gcry_mpi_new(0)));
1473  gcry_mpi_powm(tmp, elgamal_g, preshare, elgamal_p);
1474 
1475  cmp_result = gcry_mpi_cmp(tmp, info->preshare_commitment);
1476  gcry_mpi_release(tmp);
1477  tmp = NULL;
1478  if (0 != cmp_result)
1479  {
1480  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "P%u: Got invalid presecret from P%u\n",
1481  (unsigned int)ks->local_peer_idx, (unsigned int)(info - ks->info));
1482  return;
1483  }
1484 
1485  if (NULL == ks->my_share)
1486  {
1487  GNUNET_assert(NULL != (ks->my_share = gcry_mpi_new(0)));
1488  }
1489  gcry_mpi_addm(ks->my_share, ks->my_share, preshare, elgamal_q);
1490 
1491  for (j = 0; j < ks->num_peers; j++)
1492  {
1493  gcry_mpi_t presigma;
1494  if (NULL == ks->info[j].sigma)
1495  {
1496  GNUNET_assert(NULL != (ks->info[j].sigma = gcry_mpi_new(0)));
1497  gcry_mpi_set_ui(ks->info[j].sigma, 1);
1498  }
1499  presigma = keygen_reveal_get_exp_preshare(ks, d, j);
1500  gcry_mpi_mulm(ks->info[j].sigma, ks->info[j].sigma, presigma, elgamal_p);
1501  gcry_mpi_release(presigma);
1502  }
1503 
1504  gcry_mpi_t prod;
1505  GNUNET_assert(NULL != (prod = gcry_mpi_new(0)));
1506  gcry_mpi_t j_to_k;
1507  GNUNET_assert(NULL != (j_to_k = gcry_mpi_new(0)));
1508  // validate that the polynomial sharing matches the additive sharing
1509  for (j = 0; j < ks->num_peers; j++)
1510  {
1511  unsigned int k;
1512  int cmp_result;
1513  gcry_mpi_t exp_preshare;
1514  gcry_mpi_set_ui(prod, 1);
1515  for (k = 0; k < ks->threshold; k++)
1516  {
1517  // Using pow(double,double) is a bit sketchy.
1518  // We count players from 1, but shares from 0.
1519  gcry_mpi_t tmp;
1520  gcry_mpi_set_ui(j_to_k, (unsigned int)pow(j + 1, k));
1521  tmp = keygen_reveal_get_exp_coeff(ks, d, k);
1522  gcry_mpi_powm(tmp, tmp, j_to_k, elgamal_p);
1523  gcry_mpi_mulm(prod, prod, tmp, elgamal_p);
1524  gcry_mpi_release(tmp);
1525  }
1526  exp_preshare = keygen_reveal_get_exp_preshare(ks, d, j);
1527  gcry_mpi_mod(exp_preshare, exp_preshare, elgamal_p);
1528  cmp_result = gcry_mpi_cmp(prod, exp_preshare);
1529  gcry_mpi_release(exp_preshare);
1530  exp_preshare = NULL;
1531  if (0 != cmp_result)
1532  {
1533  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "P%u: reveal data from P%u incorrect\n",
1534  ks->local_peer_idx, j);
1535  /* no need for further verification, round2 stays invalid ... */
1536  return;
1537  }
1538  }
1539 
1540  // TODO: verify proof of fair encryption (once implemented)
1541  for (j = 0; j < ks->num_peers; j++)
1542  {
1544  if (GNUNET_YES != verify_fair(&ks->info[j].paillier_public_key, fe))
1545  {
1546  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "P%u: reveal data from P%u incorrect (fair encryption)\n",
1547  ks->local_peer_idx, j);
1548  return;
1549  }
1550  }
1551 
1552  info->round2_valid = GNUNET_YES;
1553 
1554  gcry_mpi_release(preshare);
1555  gcry_mpi_release(prod);
1556  gcry_mpi_release(j_to_k);
1557 }
static gcry_mpi_t keygen_reveal_get_exp_preshare(struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
gcry_mpi_t preshare_commitment
Commitment to the preshare that is intended for our peer.
int round1_valid
Did we successfully receive the round1 element of the peer?
static struct KeygenPeerInfo * get_keygen_peer_info(const struct KeygenSession *ks, const struct GNUNET_PeerIdentity *peer)
Get the peer info belonging to a peer identity in a keygen session.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
struct GNUNET_CRYPTO_EddsaSignature signature
Signature over rest of the message.
static gcry_mpi_t keygen_reveal_get_exp_coeff(struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
gcry_mpi_t my_share
Share of our peer.
#define GNUNET_NO
Definition: gnunet_common.h:78
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
unsigned int threshold
Minimum number of shares required to restore the secret.
const void * data
Actual data of the element.
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
int round2_valid
Did we successfully receive the round2 element of the peer?
gcry_mpi_t public_key
Public key, will be updated when a round2 element arrives.
int GNUNET_CRYPTO_eddsa_verify(uint32_t purpose, const struct GNUNET_CRYPTO_EccSignaturePurpose *validate, const struct GNUNET_CRYPTO_EddsaSignature *sig, const struct GNUNET_CRYPTO_EddsaPublicKey *pub)
Verify EdDSA signature.
Definition: crypto_ecc.c:1116
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static int verify_fair(const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, const struct GNUNET_SECRETSHARING_FairEncryption *fe)
Session to establish a threshold-shared secret.
void GNUNET_CRYPTO_paillier_decrypt(const struct GNUNET_CRYPTO_PaillierPrivateKey *private_key, const struct GNUNET_CRYPTO_PaillierPublicKey *public_key, const struct GNUNET_CRYPTO_PaillierCiphertext *ciphertext, gcry_mpi_t m)
Decrypt a paillier ciphertext with a private key.
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!)...
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
unsigned int local_peer_idx
Index of the local peer in the ordered list of peers in the session.
struct GNUNET_CRYPTO_PaillierPublicKey paillier_public_key
The peer&#39;s paillier public key.
static void restore_fair(const struct GNUNET_CRYPTO_PaillierPublicKey *ppub, const struct GNUNET_SECRETSHARING_FairEncryption *fe, gcry_mpi_t x, gcry_mpi_t xres)
unsigned int num_peers
Total number of peers.
struct GNUNET_CRYPTO_PaillierPrivateKey paillier_private_key
Paillier private key of our peer.
static struct GNUNET_SECRETSHARING_FairEncryption * keygen_reveal_get_enc_preshare(struct KeygenSession *ks, const struct GNUNET_SECRETSHARING_KeygenRevealData *d, unsigned int idx)
struct KeygenPeerInfo * info
Information about all participating peers.
Info about a peer in a key generation session.
struct GNUNET_PeerIdentity peer
Peer that inserts this element.
uint16_t size
Number of bytes in the buffer pointed to by data.
#define GNUNET_log(kind,...)
#define GNUNET_YES
Definition: gnunet_common.h:77
gcry_mpi_t sigma
Sigma (exponentiated share) for this peer.
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
const char * GNUNET_i2s(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
#define GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG2
Signature for the second round of distributed key generation.
struct GNUNET_CRYPTO_PaillierCiphertext c
struct GNUNET_CRYPTO_EddsaPublicKey public_key
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ keygen_round1_conclude()

static void keygen_round1_conclude ( void *  cls)
static

Called when the first consensus round has concluded.

Will initiate the second round.

Parameters
clsclosure

Definition at line 1567 of file gnunet-service-secretsharing.c.

References KeygenSession::consensus, KeygenSession::deadline, GNUNET_CONSENSUS_conclude(), GNUNET_CONSENSUS_create(), GNUNET_CONSENSUS_destroy(), insert_round2_element(), keygen_round2_conclude(), keygen_round2_new_element(), KeygenSession::num_peers, KeygenSession::peers, KeygenSession::session_id, KeygenSession::start_time, and time_between().

Referenced by handle_client_keygen().

1568 {
1569  struct KeygenSession *ks = cls;
1570 
1572 
1574  time_between(ks->start_time, ks->deadline, 1, 2),
1575  ks->deadline,
1577 
1579 
1582  ks);
1583 }
static const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration of this service.
void GNUNET_CONSENSUS_destroy(struct GNUNET_CONSENSUS_Handle *consensus)
Destroy a consensus handle (free all state associated with it, no longer call any of the callbacks)...
static void insert_round2_element(struct KeygenSession *ks)
Insert round 2 element in the consensus, consisting of (1) The exponentiated pre-share polynomial coe...
static void keygen_round2_conclude(void *cls)
struct GNUNET_TIME_Absolute start_time
When does the DKG start? Necessary to compute fractions of the operation&#39;s desired time interval...
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
Session to establish a threshold-shared secret.
struct GNUNET_HashCode session_id
Identifier for this session.
unsigned int num_peers
Total number of peers.
static void keygen_round2_new_element(void *cls, const struct GNUNET_SET_Element *element)
static struct GNUNET_TIME_Absolute time_between(struct GNUNET_TIME_Absolute start, struct GNUNET_TIME_Absolute end, int num, int denum)
Interpolate between two points in time.
struct GNUNET_TIME_Absolute deadline
When would we like the key to be established?
struct GNUNET_PeerIdentity * peers
List of all peers involved in the secret sharing session.
void GNUNET_CONSENSUS_conclude(struct GNUNET_CONSENSUS_Handle *consensus, GNUNET_CONSENSUS_ConcludeCallback conclude, void *conclude_cls)
We are done with inserting new elements into the consensus; try to conclude the consensus within a gi...
struct GNUNET_CONSENSUS_Handle * GNUNET_CONSENSUS_create(const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned int num_peers, const struct GNUNET_PeerIdentity *peers, const struct GNUNET_HashCode *session_id, struct GNUNET_TIME_Absolute start, struct GNUNET_TIME_Absolute deadline, GNUNET_CONSENSUS_ElementCallback new_element_cb, void *new_element_cls)
Create a consensus session.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ insert_round1_element()

static void insert_round1_element ( struct KeygenSession ks)
static

Insert the ephemeral key and the presecret commitment of this peer in the consensus of the given session.

Parameters
kssession to use

Definition at line 1593 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_KeygenCommitData::commitment, KeygenSession::consensus, GNUNET_SET_Element::data, elgamal_g, elgamal_p, GNUNET_assert, GNUNET_CONSENSUS_insert(), GNUNET_CRYPTO_eddsa_sign(), GNUNET_CRYPTO_hash(), GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_free, GNUNET_malloc, GNUNET_OK, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG1, KeygenSession::info, KeygenSession::local_peer_idx, my_peer, KeygenPeerInfo::paillier_public_key, GNUNET_SECRETSHARING_KeygenCommitData::peer, KeygenSession::presecret_polynomial, GNUNET_SECRETSHARING_KeygenCommitData::pubkey, GNUNET_SECRETSHARING_KeygenCommitData::purpose, GNUNET_CRYPTO_EccSignaturePurpose::purpose, GNUNET_SECRETSHARING_KeygenCommitData::signature, GNUNET_CRYPTO_EccSignaturePurpose::size, and GNUNET_SET_Element::size.

Referenced by handle_client_keygen().

1594 {
1595  struct GNUNET_SET_Element *element;
1597  // g^a_{i,0}
1598  gcry_mpi_t v;
1599  // big-endian representation of 'v'
1600  unsigned char v_data[GNUNET_SECRETSHARING_ELGAMAL_BITS / 8];
1601 
1602  element = GNUNET_malloc(sizeof *element + sizeof *d);
1603  d = (void *)&element[1];
1604  element->data = d;
1605  element->size = sizeof *d;
1606 
1607  d->peer = my_peer;
1608 
1609  GNUNET_assert(0 != (v = gcry_mpi_new(GNUNET_SECRETSHARING_ELGAMAL_BITS)));
1610 
1611  gcry_mpi_powm(v, elgamal_g, ks->presecret_polynomial[0], elgamal_p);
1612 
1614 
1616 
1618 
1619  d->purpose.size = htonl((sizeof *d) - offsetof(struct GNUNET_SECRETSHARING_KeygenCommitData, purpose));
1623  &d->purpose,
1624  &d->signature));
1625 
1626  GNUNET_CONSENSUS_insert(ks->consensus, element, NULL, NULL);
1627 
1628  gcry_mpi_release(v);
1629  GNUNET_free(element);
1630 }
struct GNUNET_CRYPTO_EddsaSignature signature
Signature over the rest of the message.
#define GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DKG1
Signature for the first round of distributed key generation.
struct GNUNET_PeerIdentity peer
Peer that inserts this element.
uint32_t purpose
What does this signature vouch for? This must contain a GNUNET_SIGNATURE_PURPOSE_XXX constant (from g...
Element stored in a set.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
int GNUNET_CRYPTO_eddsa_sign(const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose, struct GNUNET_CRYPTO_EddsaSignature *sig)
EdDSA sign a given block.
Definition: crypto_ecc.c:989
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
struct GNUNET_CRYPTO_PaillierPublicKey pubkey
Ephemeral paillier public key used by &#39;peer&#39; for this session.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
void GNUNET_CONSENSUS_insert(struct GNUNET_CONSENSUS_Handle *consensus, const struct GNUNET_SET_Element *element, GNUNET_CONSENSUS_InsertDoneCallback idc, void *idc_cls)
Insert an element in the set being reconsiled.
const void * data
Actual data of the element.
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:44
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static struct GNUNET_CRYPTO_EddsaPrivateKey * my_peer_private_key
Peer that runs this service.
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!)...
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
unsigned int local_peer_idx
Index of the local peer in the ordered list of peers in the session.
struct GNUNET_HashCode commitment
Commitment of &#39;peer&#39; to its presecret.
struct GNUNET_CRYPTO_PaillierPublicKey paillier_public_key
The peer&#39;s paillier public key.
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
Signature purpose for signing the keygen commit data.
struct KeygenPeerInfo * info
Information about all participating peers.
gcry_mpi_t * presecret_polynomial
Randomly generated coefficients of the polynomial for sharing our pre-secret, where &#39;preshares[0]&#39; is...
uint16_t size
Number of bytes in the buffer pointed to by data.
#define GNUNET_malloc(size)
Wrapper around malloc.
#define GNUNET_free(ptr)
Wrapper around free.
Consensus element data used in the first round of key generation.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ check_client_keygen()

static int check_client_keygen ( void *  cls,
const struct GNUNET_SECRETSHARING_CreateMessage msg 
)
static

Check that msg is well-formed.

Parameters
clsidentification of the client
msgthe actual message
Returns
GNUNET_OK if msg is well-formed

Definition at line 1641 of file gnunet-service-secretsharing.c.

References GNUNET_break, GNUNET_OK, GNUNET_SYSERR, GNUNET_SECRETSHARING_CreateMessage::header, num_peers, GNUNET_SECRETSHARING_CreateMessage::num_peers, and GNUNET_MessageHeader::size.

1643 {
1644  unsigned int num_peers = ntohs(msg->num_peers);
1645 
1646  if (ntohs(msg->header.size) - sizeof(*msg) !=
1647  num_peers * sizeof(struct GNUNET_PeerIdentity))
1648  {
1649  GNUNET_break(0);
1650  return GNUNET_SYSERR;
1651  }
1652  return GNUNET_OK;
1653 }
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE.
Definition: secretsharing.h:50
#define GNUNET_SYSERR
Definition: gnunet_common.h:76
static unsigned int num_peers
The identity of the host (wraps the signing key of the peer).
uint16_t num_peers
Number of peers at the end of this message.
Definition: secretsharing.h:76

◆ handle_client_keygen()

static void handle_client_keygen ( void *  cls,
const struct GNUNET_SECRETSHARING_CreateMessage msg 
)
static

Functions with this signature are called whenever a message is received.

Parameters
clsidentification of the client
msgthe actual message

Definition at line 1664 of file gnunet-service-secretsharing.c.

References ClientState::client, KeygenSession::consensus, KeygenSession::cs, GNUNET_SECRETSHARING_CreateMessage::deadline, KeygenSession::deadline, generate_presecret_polynomial(), GNUNET_break, GNUNET_CONSENSUS_conclude(), GNUNET_CONSENSUS_create(), GNUNET_CRYPTO_paillier_create(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_INFO, GNUNET_log, GNUNET_new, GNUNET_new_array, GNUNET_SERVICE_client_continue(), GNUNET_SERVICE_client_drop(), GNUNET_TIME_absolute_ntoh(), KeygenSession::info, insert_round1_element(), keygen_round1_conclude(), keygen_round1_new_element(), ClientState::keygen_session, KeygenSession::local_peer_idx, normalize_peers(), GNUNET_SECRETSHARING_CreateMessage::num_peers, KeygenSession::num_peers, KeygenSession::paillier_private_key, KeygenPeerInfo::paillier_public_key, KeygenPeerInfo::peer, KeygenSession::peers, GNUNET_SECRETSHARING_CreateMessage::threshold, and KeygenSession::threshold.

1666 {
1667  struct ClientState *cs = cls;
1668  struct KeygenSession *ks;
1669 
1671  "client requested key generation\n");
1672  if (NULL != cs->keygen_session)
1673  {
1674  GNUNET_break(0);
1676  return;
1677  }
1678  ks = GNUNET_new(struct KeygenSession);
1679  ks->cs = cs;
1680  cs->keygen_session = ks;
1682  ks->threshold = ntohs(msg->threshold);
1683  ks->num_peers = ntohs(msg->num_peers);
1684 
1685  ks->peers = normalize_peers((struct GNUNET_PeerIdentity *)&msg[1],
1686  ks->num_peers,
1687  &ks->num_peers,
1688  &ks->local_peer_idx);
1689 
1690 
1692  "first round of consensus with %u peers\n",
1693  ks->num_peers);
1695  ks->num_peers,
1696  ks->peers,
1697  &msg->session_id,
1701  ks);
1702 
1703  ks->info = GNUNET_new_array(ks->num_peers,
1704  struct KeygenPeerInfo);
1705 
1706  for (unsigned int i = 0; i < ks->num_peers; i++)
1707  ks->info[i].peer = ks->peers[i];
1708 
1710  &ks->paillier_private_key);
1711 
1713  "P%u: Generated paillier key pair\n",
1714  ks->local_peer_idx);
1717  "P%u: Generated presecret polynomial\n",
1718  ks->local_peer_idx);
1721  "P%u: Concluding for round 1\n",
1722  ks->local_peer_idx);
1725  ks);
1728  "P%u: Waiting for round 1 elements ...\n",
1729  ks->local_peer_idx);
1730 }
struct GNUNET_TIME_AbsoluteNBO start
Start time for communication with the other peers.
Definition: secretsharing.h:60
static void insert_round1_element(struct KeygenSession *ks)
Insert the ephemeral key and the presecret commitment of this peer in the consensus of the given sess...
static void keygen_round1_conclude(void *cls)
Called when the first consensus round has concluded.
static const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration of this service.
State we keep per client.
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_ntoh(struct GNUNET_TIME_AbsoluteNBO a)
Convert absolute time from network byte order.
Definition: time.c:671
static void generate_presecret_polynomial(struct KeygenSession *ks)
Generate the random coefficients of our pre-secret polynomial.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
unsigned int threshold
Minimum number of shares required to restore the secret.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
void GNUNET_CRYPTO_paillier_create(struct GNUNET_CRYPTO_PaillierPublicKey *public_key, struct GNUNET_CRYPTO_PaillierPrivateKey *private_key)
Create a freshly generated paillier public key.
struct GNUNET_CONSENSUS_Handle * consensus
Current consensus, used for both DKG rounds.
struct GNUNET_TIME_AbsoluteNBO deadline
Deadline for the establishment of the crypto system.
Definition: secretsharing.h:65
Session to establish a threshold-shared secret.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
static struct GNUNET_PeerIdentity * normalize_peers(struct GNUNET_PeerIdentity *listed, unsigned int num_listed, unsigned int *num_normalized, unsigned int *my_peer_idx)
Normalize the given list of peers, by including the local peer (if it is missing) and sorting the pee...
unsigned int local_peer_idx
Index of the local peer in the ordered list of peers in the session.
void GNUNET_SERVICE_client_drop(struct GNUNET_SERVICE_Client *c)
Ask the server to disconnect from the given client.
Definition: service.c:2315
uint16_t threshold
Mininum number of cooperating peers to decrypt a value.
Definition: secretsharing.h:71
struct GNUNET_CRYPTO_PaillierPublicKey paillier_public_key
The peer&#39;s paillier public key.
unsigned int num_peers
Total number of peers.
struct KeygenSession * keygen_session
Keygen session of the client, if any.
struct GNUNET_CRYPTO_PaillierPrivateKey paillier_private_key
Paillier private key of our peer.
struct KeygenPeerInfo * info
Information about all participating peers.
Info about a peer in a key generation session.
struct GNUNET_TIME_Absolute deadline
When would we like the key to be established?
The identity of the host (wraps the signing key of the peer).
static void keygen_round1_new_element(void *cls, const struct GNUNET_SET_Element *element)
Consensus element handler for round one.
struct GNUNET_SERVICE_Client * client
Client this is about.
struct GNUNET_PeerIdentity * peers
List of all peers involved in the secret sharing session.
#define GNUNET_log(kind,...)
void GNUNET_CONSENSUS_conclude(struct GNUNET_CONSENSUS_Handle *consensus, GNUNET_CONSENSUS_ConcludeCallback conclude, void *conclude_cls)
We are done with inserting new elements into the consensus; try to conclude the consensus within a gi...
struct GNUNET_PeerIdentity peer
Peer identity of the peer.
uint16_t num_peers
Number of peers at the end of this message.
Definition: secretsharing.h:76
struct GNUNET_CONSENSUS_Handle * GNUNET_CONSENSUS_create(const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned int num_peers, const struct GNUNET_PeerIdentity *peers, const struct GNUNET_HashCode *session_id, struct GNUNET_TIME_Absolute start, struct GNUNET_TIME_Absolute deadline, GNUNET_CONSENSUS_ElementCallback new_element_cb, void *new_element_cls)
Create a consensus session.
struct GNUNET_HashCode session_id
Session ID, will be used for consensus.
Definition: secretsharing.h:55
void GNUNET_SERVICE_client_continue(struct GNUNET_SERVICE_Client *c)
Continue receiving further messages from the given client.
Definition: service.c:2234
struct ClientState * cs
Which client is this for?
Here is the call graph for this function:

◆ decrypt_conclude()

static void decrypt_conclude ( void *  cls)
static

Called when the partial decryption consensus concludes.

Definition at line 1737 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_Ciphertext::c2_bits, DecryptSession::ciphertext, compute_lagrange_coefficient(), DecryptSession::consensus, DecryptSession::cs, ds, elgamal_p, GNUNET_assert, GNUNET_CONSENSUS_destroy(), GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_ERROR_TYPE_INFO, GNUNET_free, GNUNET_log, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT_DONE, GNUNET_MQ_msg, GNUNET_MQ_send(), GNUNET_new_array, GNUNET_SECRETSHARING_ELGAMAL_BITS, DecryptSession::info, m, ClientState::mq, msg, GNUNET_SECRETSHARING_Share::my_peer, GNUNET_SECRETSHARING_Share::num_peers, DecryptPeerInfo::original_index, DecryptPeerInfo::partial_decryption, GNUNET_SECRETSHARING_DecryptResponseMessage::plaintext, DecryptSession::share, and GNUNET_SECRETSHARING_DecryptResponseMessage::success.

Referenced by handle_client_decrypt().

1738 {
1739  struct DecryptSession *ds = cls;
1741  struct GNUNET_MQ_Envelope *ev;
1742  gcry_mpi_t lagrange;
1743  gcry_mpi_t m;
1744  gcry_mpi_t tmp;
1745  gcry_mpi_t c_2;
1746  gcry_mpi_t prod;
1747  unsigned int *indices;
1748  unsigned int num;
1749  unsigned int i;
1750  unsigned int j;
1751 
1753  ds->consensus = NULL;
1754 
1755  GNUNET_assert(0 != (lagrange = gcry_mpi_new(0)));
1756  GNUNET_assert(0 != (m = gcry_mpi_new(0)));
1757  GNUNET_assert(0 != (tmp = gcry_mpi_new(0)));
1758  GNUNET_assert(0 != (prod = gcry_mpi_new(0)));
1759 
1760  num = 0;
1761  for (i = 0; i < ds->share->num_peers; i++)
1762  if (NULL != ds->info[i].partial_decryption)
1763  num++;
1764 
1765  indices = GNUNET_new_array(num,
1766  unsigned int);
1767  j = 0;
1768  for (i = 0; i < ds->share->num_peers; i++)
1769  if (NULL != ds->info[i].partial_decryption)
1770  indices[j++] = ds->info[i].original_index;
1771 
1773  "P%u: decrypt conclude, with %u peers\n",
1774  ds->share->my_peer,
1775  num);
1776 
1777  gcry_mpi_set_ui(prod, 1);
1778  for (i = 0; i < num; i++)
1779  {
1781  "P%u: index of %u: %u\n",
1782  ds->share->my_peer, i, indices[i]);
1783  compute_lagrange_coefficient(lagrange, indices[i], indices, num);
1784  // w_i^{\lambda_i}
1785  gcry_mpi_powm(tmp, ds->info[indices[i]].partial_decryption, lagrange, elgamal_p);
1786 
1787  // product of all exponentiated partiel decryptions ...
1788  gcry_mpi_mulm(prod, prod, tmp, elgamal_p);
1789  }
1790 
1792 
1793  GNUNET_assert(0 != gcry_mpi_invm(prod, prod, elgamal_p));
1794  gcry_mpi_mulm(m, c_2, prod, elgamal_p);
1797  msg->success = htonl(1);
1798  GNUNET_MQ_send(ds->cs->mq,
1799  ev);
1800 
1801  GNUNET_log(GNUNET_ERROR_TYPE_INFO, "sent decrypt done to client\n");
1802 
1803  GNUNET_free(indices);
1804 
1805  gcry_mpi_release(lagrange);
1806  gcry_mpi_release(m);
1807  gcry_mpi_release(tmp);
1808  gcry_mpi_release(prod);
1809  gcry_mpi_release(c_2);
1810 
1811  // FIXME: what if not enough peers participated?
1812 }
void GNUNET_CONSENSUS_destroy(struct GNUNET_CONSENSUS_Handle *consensus)
Destroy a consensus handle (free all state associated with it, no longer call any of the callbacks)...
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
struct GNUNET_SECRETSHARING_FieldElement plaintext
Decrypted plaintext.
struct GNUNET_MQ_Handle * mq
MQ to talk to client.
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
#define GNUNET_MQ_msg(mvar, type)
Allocate a GNUNET_MQ_Envelope.
Definition: gnunet_mq_lib.h:67
gcry_mpi_t partial_decryption
Set to the partial decryption of this peer, or NULL if we did not receive a partial decryption from t...
static struct GNUNET_ARM_MonitorHandle * m
Monitor connection with ARM.
Definition: gnunet-arm.c:99
#define GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT_DONE
The service succeeded in decrypting a ciphertext.
static void compute_lagrange_coefficient(gcry_mpi_t coeff, unsigned int j, unsigned int *indices, unsigned int num)
Get a the j-th lagrange coefficient for a set of indices.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
struct DecryptPeerInfo * info
State information about other peers.
struct ClientState * cs
Which client is this for?
struct GNUNET_CONSENSUS_Handle * consensus
Handle to the consensus over partial decryptions.
unsigned int original_index
Original index in the key generation round.
uint32_t success
Zero if decryption failed, non-zero if decryption succeeded.
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
uint16_t my_peer
Index of our peer in the list.
#define GNUNET_log(kind,...)
static struct GNUNET_FS_DirScanner * ds
Handle to the directory scanner (for recursive insertions).
void GNUNET_MQ_send(struct GNUNET_MQ_Handle *mq, struct GNUNET_MQ_Envelope *ev)
Send a message with the given message queue.
Definition: mq.c:351
uint16_t num_peers
Peers that have the share.
uint32_t c2_bits[1024/8/sizeof(uint32_t)]
Session to cooperatively decrypt a value.
#define GNUNET_free(ptr)
Wrapper around free.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ mpi_to_str()

static char* mpi_to_str ( gcry_mpi_t  mpi)
static

Get a string representation of an MPI.

The caller must free the returned string.

Parameters
mpimpi to convert to a string
Returns
string representation of mpi, must be free'd by the caller

Definition at line 1823 of file gnunet-service-secretsharing.c.

References buf, and GNUNET_assert.

Referenced by decrypt_new_element(), and insert_decrypt_element().

1824 {
1825  unsigned char *buf;
1826 
1827  GNUNET_assert(0 == gcry_mpi_aprint(GCRYMPI_FMT_HEX, &buf, NULL, mpi));
1828  return (char *)buf;
1829 }
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static char buf[2048]
Here is the caller graph for this function:

◆ decrypt_new_element()

static void decrypt_new_element ( void *  cls,
const struct GNUNET_SET_Element element 
)
static

Called when a new partial decryption arrives.

Definition at line 1836 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_Ciphertext::c1_bits, ciphertext, GNUNET_SECRETSHARING_DecryptData::ciphertext, DecryptSession::ciphertext, cleanup(), GNUNET_SET_Element::data, elgamal_g, elgamal_p, get_decrypt_peer_info(), GNUNET_assert, GNUNET_CRYPTO_hash(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_ERROR_TYPE_ERROR, GNUNET_ERROR_TYPE_WARNING, GNUNET_free, GNUNET_i2s(), GNUNET_log, GNUNET_memcmp, GNUNET_SECRETSHARING_ELGAMAL_BITS, DecryptSession::info, mpi_to_str(), GNUNET_SECRETSHARING_Share::my_peer, DecryptPeerInfo::partial_decryption, GNUNET_SECRETSHARING_DecryptData::peer, DecryptSession::share, KeygenPeerInfo::sigma, GNUNET_SECRETSHARING_Share::sigmas, and GNUNET_SET_Element::size.

Referenced by handle_client_decrypt().

1838 {
1839  struct DecryptSession *session = cls;
1840  const struct GNUNET_SECRETSHARING_DecryptData *d;
1841  struct DecryptPeerInfo *info;
1842  struct GNUNET_HashCode challenge_hash;
1843 
1844  /* nizk response */
1845  gcry_mpi_t r;
1846  /* nizk challenge */
1847  gcry_mpi_t challenge;
1848  /* nizk commit1, g^\beta */
1849  gcry_mpi_t commit1;
1850  /* nizk commit2, c_1^\beta */
1851  gcry_mpi_t commit2;
1852  /* homomorphic commitment to the peer's share,
1853  * public key share */
1854  gcry_mpi_t sigma;
1855  /* partial decryption we received */
1856  gcry_mpi_t w;
1857  /* ciphertext component #1 */
1858  gcry_mpi_t c1;
1859  /* temporary variable (for comparision) #1 */
1860  gcry_mpi_t tmp1;
1861  /* temporary variable (for comparision) #2 */
1862  gcry_mpi_t tmp2;
1863 
1864  if (NULL == element)
1865  {
1866  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "decryption failed\n");
1867  /* FIXME: destroy */
1868  return;
1869  }
1870 
1871  if (element->size != sizeof *d)
1872  {
1873  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "element of wrong size in decrypt consensus\n");
1874  return;
1875  }
1876 
1877  d = element->data;
1878 
1879  info = get_decrypt_peer_info(session, &d->peer);
1880 
1881  if (NULL == info)
1882  {
1883  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "decrypt element from invalid peer (%s)\n",
1884  GNUNET_i2s(&d->peer));
1885  return;
1886  }
1887 
1888  if (NULL != info->partial_decryption)
1889  {
1890  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "decrypt element duplicate\n");
1891  return;
1892  }
1893 
1894  if (0 != GNUNET_memcmp(&d->ciphertext, &session->ciphertext))
1895  {
1896  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "P%u: got decrypt element with non-matching ciphertext from P%u\n",
1897  (unsigned int)session->share->my_peer, (unsigned int)(info - session->info));
1898 
1899  return;
1900  }
1901 
1902 
1903  GNUNET_CRYPTO_hash(offsetof(struct GNUNET_SECRETSHARING_DecryptData, ciphertext) + (char *)d,
1904  offsetof(struct GNUNET_SECRETSHARING_DecryptData, nizk_response) -
1905  offsetof(struct GNUNET_SECRETSHARING_DecryptData, ciphertext),
1906  &challenge_hash);
1907 
1908  GNUNET_CRYPTO_mpi_scan_unsigned(&challenge, &challenge_hash,
1909  sizeof(struct GNUNET_HashCode));
1910 
1911  GNUNET_CRYPTO_mpi_scan_unsigned(&sigma, &session->share->sigmas[info - session->info],
1912  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1913 
1915  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1916 
1917  GNUNET_CRYPTO_mpi_scan_unsigned(&commit1, &d->nizk_commit1,
1918  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1919 
1920  GNUNET_CRYPTO_mpi_scan_unsigned(&commit2, &d->nizk_commit2,
1921  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1922 
1923  GNUNET_CRYPTO_mpi_scan_unsigned(&r, &d->nizk_response,
1924  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1925 
1926  GNUNET_CRYPTO_mpi_scan_unsigned(&w, &d->partial_decryption,
1927  sizeof(struct GNUNET_SECRETSHARING_FieldElement));
1928 
1929  GNUNET_assert(NULL != (tmp1 = gcry_mpi_new(0)));
1930  GNUNET_assert(NULL != (tmp2 = gcry_mpi_new(0)));
1931 
1932  // tmp1 = g^r
1933  gcry_mpi_powm(tmp1, elgamal_g, r, elgamal_p);
1934 
1935  // tmp2 = g^\beta * \sigma^challenge
1936  gcry_mpi_powm(tmp2, sigma, challenge, elgamal_p);
1937  gcry_mpi_mulm(tmp2, tmp2, commit1, elgamal_p);
1938 
1939  if (0 != gcry_mpi_cmp(tmp1, tmp2))
1940  {
1941  char *tmp1_str;
1942  char *tmp2_str;
1943 
1944  tmp1_str = mpi_to_str(tmp1);
1945  tmp2_str = mpi_to_str(tmp2);
1947  "P%u: Received invalid partial decryption from P%u (eqn 1), expected %s got %s\n",
1948  session->share->my_peer,
1949  (unsigned int)(info - session->info),
1950  tmp1_str,
1951  tmp2_str);
1952  GNUNET_free(tmp1_str);
1953  GNUNET_free(tmp2_str);
1954  goto cleanup;
1955  }
1956 
1957 
1958  gcry_mpi_powm(tmp1, c1, r, elgamal_p);
1959 
1960  gcry_mpi_powm(tmp2, w, challenge, elgamal_p);
1961  gcry_mpi_mulm(tmp2, tmp2, commit2, elgamal_p);
1962 
1963 
1964  if (0 != gcry_mpi_cmp(tmp1, tmp2))
1965  {
1967  "P%u: Received invalid partial decryption from P%u (eqn 2)\n",
1968  session->share->my_peer,
1969  (unsigned int)(info - session->info));
1970  goto cleanup;
1971  }
1972 
1973 
1974  GNUNET_CRYPTO_mpi_scan_unsigned(&info->partial_decryption, &d->partial_decryption,
1976 cleanup:
1977  gcry_mpi_release(tmp1);
1978  gcry_mpi_release(tmp2);
1979  gcry_mpi_release(sigma);
1980  gcry_mpi_release(commit1);
1981  gcry_mpi_release(commit2);
1982  gcry_mpi_release(r);
1983  gcry_mpi_release(w);
1984  gcry_mpi_release(challenge);
1985  gcry_mpi_release(c1);
1986 }
static char * mpi_to_str(gcry_mpi_t mpi)
Get a string representation of an MPI.
Information about a peer in a decrypt session.
struct GNUNET_PeerIdentity peer
Peer that inserts this element.
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
static struct DecryptPeerInfo * get_decrypt_peer_info(const struct DecryptSession *ds, const struct GNUNET_PeerIdentity *peer)
Get the peer info belonging to a peer identity in a decrypt session.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
Data of then element put in consensus for decrypting a value.
gcry_mpi_t partial_decryption
Set to the partial decryption of this peer, or NULL if we did not receive a partial decryption from t...
const void * data
Actual data of the element.
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:44
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static void cleanup(void *cls)
Function scheduled as very last function, cleans up after us.
static struct GNUNET_SECRETSHARING_Ciphertext ciphertext
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
A 512-bit hashcode.
uint32_t c1_bits[1024/8/sizeof(uint32_t)]
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
struct DecryptPeerInfo * info
State information about other peers.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
struct GNUNET_SECRETSHARING_FieldElement * sigmas
uint16_t my_peer
Index of our peer in the list.
uint16_t size
Number of bytes in the buffer pointed to by data.
#define GNUNET_log(kind,...)
const char * GNUNET_i2s(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
Session to cooperatively decrypt a value.
#define GNUNET_free(ptr)
Wrapper around free.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ insert_decrypt_element()

static void insert_decrypt_element ( struct DecryptSession ds)
static

Definition at line 1990 of file gnunet-service-secretsharing.c.

References beta, GNUNET_SECRETSHARING_Ciphertext::c1_bits, ciphertext, GNUNET_SECRETSHARING_DecryptData::ciphertext, DecryptSession::ciphertext, DecryptSession::consensus, GNUNET_SET_Element::data, GNUNET_SET_Element::element_type, elgamal_g, elgamal_p, elgamal_q, GNUNET_assert, GNUNET_CONSENSUS_insert(), GNUNET_CRYPTO_eddsa_sign(), GNUNET_CRYPTO_hash(), GNUNET_CRYPTO_mpi_print_unsigned(), GNUNET_CRYPTO_mpi_scan_unsigned(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_ERROR, GNUNET_free, GNUNET_log, GNUNET_OK, GNUNET_SECRETSHARING_ELGAMAL_BITS, GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DECRYPTION, mpi_to_str(), GNUNET_SECRETSHARING_Share::my_peer, my_peer, GNUNET_SECRETSHARING_Share::my_share, GNUNET_SECRETSHARING_DecryptData::nizk_commit1, GNUNET_SECRETSHARING_DecryptData::nizk_commit2, GNUNET_SECRETSHARING_DecryptData::nizk_response, GNUNET_SECRETSHARING_Share::num_peers, GNUNET_SECRETSHARING_DecryptData::partial_decryption, GNUNET_SECRETSHARING_DecryptData::peer, GNUNET_SECRETSHARING_DecryptData::purpose, DecryptSession::share, KeygenPeerInfo::sigma, GNUNET_SECRETSHARING_Share::sigmas, and GNUNET_SET_Element::size.

Referenced by handle_client_decrypt().

1991 {
1993  struct GNUNET_SET_Element element;
1994  /* our share */
1995  gcry_mpi_t s;
1996  /* partial decryption with our share */
1997  gcry_mpi_t w;
1998  /* first component of the elgamal ciphertext */
1999  gcry_mpi_t c1;
2000  /* nonce for dlog zkp */
2001  gcry_mpi_t beta;
2002  gcry_mpi_t tmp;
2003  gcry_mpi_t challenge;
2004  gcry_mpi_t sigma;
2005  struct GNUNET_HashCode challenge_hash;
2006 
2007  /* make vagrind happy until we implement the real deal ... */
2008  memset(&d, 0, sizeof d);
2009 
2010  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "P%u: Inserting decrypt element\n",
2011  ds->share->my_peer);
2012 
2013  GNUNET_assert(ds->share->my_peer < ds->share->num_peers);
2014 
2021 
2022  GNUNET_assert(NULL != (w = gcry_mpi_new(0)));
2023  GNUNET_assert(NULL != (beta = gcry_mpi_new(0)));
2024  GNUNET_assert(NULL != (tmp = gcry_mpi_new(0)));
2025 
2026  // FIXME: unnecessary, remove once crypto works
2027  gcry_mpi_powm(tmp, elgamal_g, s, elgamal_p);
2028  if (0 != gcry_mpi_cmp(tmp, sigma))
2029  {
2030  char *sigma_str = mpi_to_str(sigma);
2031  char *tmp_str = mpi_to_str(tmp);
2032  char *s_str = mpi_to_str(s);
2033  GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Share of P%u is invalid, ref sigma %s, "
2034  "computed sigma %s, s %s\n",
2035  ds->share->my_peer,
2036  sigma_str, tmp_str, s_str);
2037  GNUNET_free(sigma_str);
2038  GNUNET_free(tmp_str);
2039  GNUNET_free(s_str);
2040  }
2041 
2042  gcry_mpi_powm(w, c1, s, elgamal_p);
2043 
2044  element.data = (void *)&d;
2045  element.size = sizeof(struct GNUNET_SECRETSHARING_DecryptData);
2046  element.element_type = 0;
2047 
2048  d.ciphertext = ds->ciphertext;
2049  d.peer = my_peer;
2051 
2052  // create the zero knowledge proof
2053  // randomly choose beta such that 0 < beta < q
2054  do
2055  {
2056  gcry_mpi_randomize(beta, GNUNET_SECRETSHARING_ELGAMAL_BITS - 1, GCRY_WEAK_RANDOM);
2057  }
2058  while ((gcry_mpi_cmp_ui(beta, 0) == 0) || (gcry_mpi_cmp(beta, elgamal_q) >= 0));
2059  // tmp = g^beta
2060  gcry_mpi_powm(tmp, elgamal_g, beta, elgamal_p);
2062  // tmp = (c_1)^beta
2063  gcry_mpi_powm(tmp, c1, beta, elgamal_p);
2065 
2066  // the challenge is the hash of everything up to the response
2067  GNUNET_CRYPTO_hash(offsetof(struct GNUNET_SECRETSHARING_DecryptData, ciphertext) + (char *)&d,
2069  offsetof(struct GNUNET_SECRETSHARING_DecryptData, ciphertext),
2070  &challenge_hash);
2071 
2072  GNUNET_CRYPTO_mpi_scan_unsigned(&challenge, &challenge_hash,
2073  sizeof(struct GNUNET_HashCode));
2074 
2075  // compute the response in tmp,
2076  // tmp = (c * s + beta) mod q
2077  gcry_mpi_mulm(tmp, challenge, s, elgamal_q);
2078  gcry_mpi_addm(tmp, tmp, beta, elgamal_q);
2079 
2081 
2082  d.purpose.size = htonl(element.size - offsetof(struct GNUNET_SECRETSHARING_DecryptData, purpose));
2083  d.purpose.purpose = htonl(GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DECRYPTION);
2084 
2087  &d.purpose,
2088  &d.signature));
2089 
2090  GNUNET_CONSENSUS_insert(ds->consensus, &element, NULL, NULL);
2092  "P%u: Inserting decrypt element done!\n",
2093  ds->share->my_peer);
2094 
2095  gcry_mpi_release(s);
2096  gcry_mpi_release(w);
2097  gcry_mpi_release(c1);
2098  gcry_mpi_release(beta);
2099  gcry_mpi_release(tmp);
2100  gcry_mpi_release(challenge);
2101  gcry_mpi_release(sigma);
2102 }
static char * mpi_to_str(gcry_mpi_t mpi)
Get a string representation of an MPI.
struct GNUNET_SECRETSHARING_FieldElement my_share
Share of &#39;my_peer&#39;.
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
Element stored in a set.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
int GNUNET_CRYPTO_eddsa_sign(const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose, struct GNUNET_CRYPTO_EddsaSignature *sig)
EdDSA sign a given block.
Definition: crypto_ecc.c:989
void GNUNET_CRYPTO_mpi_print_unsigned(void *buf, size_t size, gcry_mpi_t val)
Output the given MPI value to the given buffer in network byte order.
Definition: crypto_mpi.c:75
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
Data of then element put in consensus for decrypting a value.
void GNUNET_CONSENSUS_insert(struct GNUNET_CONSENSUS_Handle *consensus, const struct GNUNET_SET_Element *element, GNUNET_CONSENSUS_InsertDoneCallback idc, void *idc_cls)
Insert an element in the set being reconsiled.
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:44
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static struct GNUNET_CRYPTO_EddsaPrivateKey * my_peer_private_key
Peer that runs this service.
static struct GNUNET_SECRETSHARING_Ciphertext ciphertext
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
A 512-bit hashcode.
uint32_t c1_bits[1024/8/sizeof(uint32_t)]
void GNUNET_CRYPTO_mpi_scan_unsigned(gcry_mpi_t *result, const void *data, size_t size)
Convert data buffer into MPI value.
Definition: crypto_mpi.c:128
struct GNUNET_SECRETSHARING_FieldElement nizk_response
Reponse to the challenge computed from the protocol transcript.
struct GNUNET_CONSENSUS_Handle * consensus
Handle to the consensus over partial decryptions.
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
struct GNUNET_SECRETSHARING_FieldElement * sigmas
uint16_t my_peer
Index of our peer in the list.
#define GNUNET_log(kind,...)
#define GNUNET_SIGNATURE_PURPOSE_SECRETSHARING_DECRYPTION
Signature for cooperatice decryption.
static float beta
Percentage of total peer number in the view to send random PULLs to.
uint16_t num_peers
Peers that have the share.
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
#define GNUNET_free(ptr)
Wrapper around free.
#define GNUNET_SECRETSHARING_ELGAMAL_BITS
Number of bits for secretsharing elements.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ check_client_decrypt()

static int check_client_decrypt ( void *  cls,
const struct GNUNET_SECRETSHARING_DecryptRequestMessage msg 
)
static

Check that msg is well-formed.

Parameters
clsidentification of the client
msgthe actual message
Returns
GNUNET_OK (check deferred a bit)

Definition at line 2113 of file gnunet-service-secretsharing.c.

References GNUNET_OK.

2115 {
2116  /* we check later, it's complicated */
2117  return GNUNET_OK;
2118 }
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75

◆ handle_client_decrypt()

static void handle_client_decrypt ( void *  cls,
const struct GNUNET_SECRETSHARING_DecryptRequestMessage msg 
)
static

Functions with this signature are called whenever a message is received.

Parameters
clsidentification of the client
msgthe actual message

Definition at line 2129 of file gnunet-service-secretsharing.c.

References GNUNET_SECRETSHARING_DecryptRequestMessage::ciphertext, DecryptSession::ciphertext, ClientState::client, DecryptSession::consensus, DecryptSession::cs, GNUNET_SECRETSHARING_DecryptRequestMessage::deadline, DecryptSession::deadline, decrypt_conclude(), decrypt_new_element(), ClientState::decrypt_session, ds, GNUNET_break, GNUNET_CONSENSUS_conclude(), GNUNET_CONSENSUS_create(), GNUNET_CRYPTO_hash(), GNUNET_ERROR_TYPE_INFO, GNUNET_log, GNUNET_new, GNUNET_new_array, GNUNET_SECRETSHARING_share_read(), GNUNET_SERVICE_client_continue(), GNUNET_SERVICE_client_drop(), GNUNET_TIME_absolute_ntoh(), GNUNET_SECRETSHARING_DecryptRequestMessage::header, DecryptSession::info, insert_decrypt_element(), GNUNET_SECRETSHARING_Share::num_peers, DecryptPeerInfo::original_index, GNUNET_SECRETSHARING_Share::original_indices, DecryptPeerInfo::peer, GNUNET_SECRETSHARING_Share::peers, DecryptSession::share, GNUNET_MessageHeader::size, GNUNET_SECRETSHARING_DecryptRequestMessage::start, and DecryptSession::start.

2131 {
2132  struct ClientState *cs = cls;
2133  struct DecryptSession *ds;
2134  struct GNUNET_HashCode session_id;
2135 
2136  if (NULL != cs->decrypt_session)
2137  {
2138  GNUNET_break(0);
2140  return;
2141  }
2142  ds = GNUNET_new(struct DecryptSession);
2143  cs->decrypt_session = ds;
2144  ds->cs = cs;
2147  ds->ciphertext = msg->ciphertext;
2148 
2149  ds->share = GNUNET_SECRETSHARING_share_read(&msg[1],
2150  ntohs(msg->header.size) - sizeof(*msg),
2151  NULL);
2152  if (NULL == ds->share)
2153  {
2154  GNUNET_break(0);
2156  return;
2157  }
2158 
2159  /* FIXME: this is probably sufficient, but kdf/hash with all values would be nicer ... */
2161  sizeof(struct GNUNET_SECRETSHARING_Ciphertext),
2162  &session_id);
2164  ds->share->num_peers,
2165  ds->share->peers,
2166  &session_id,
2167  ds->start,
2168  ds->deadline,
2170  ds);
2171 
2172 
2173  ds->info = GNUNET_new_array(ds->share->num_peers,
2174  struct DecryptPeerInfo);
2175  for (unsigned int i = 0; i < ds->share->num_peers; i++)
2176  {
2177  ds->info[i].peer = ds->share->peers[i];
2178  ds->info[i].original_index = ds->share->original_indices[i];
2179  }
2183  ds);
2186  "decrypting with %u peers\n",
2187  ds->share->num_peers);
2188 }
Information about a peer in a decrypt session.
static const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration of this service.
struct GNUNET_SECRETSHARING_Share * GNUNET_SECRETSHARING_share_read(const void *data, size_t len, size_t *readlen)
Read a share from its binary representation.
State we keep per client.
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_ntoh(struct GNUNET_TIME_AbsoluteNBO a)
Convert absolute time from network byte order.
Definition: time.c:671
struct GNUNET_SECRETSHARING_Share * share
Share of the local peer.
static void decrypt_conclude(void *cls)
Called when the partial decryption consensus concludes.
struct GNUNET_PeerIdentity * peers
Peer identities (includes &#39;my_peer&#39;)
struct GNUNET_PeerIdentity peer
Identity of the peer.
static struct GNUNET_HashCode session_id
static void decrypt_new_element(void *cls, const struct GNUNET_SET_Element *element)
Called when a new partial decryption arrives.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT_REQUEST.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
static void insert_decrypt_element(struct DecryptSession *ds)
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:44
struct DecryptSession * decrypt_session
Decrypt session of the client, if any.
#define GNUNET_new_array(n, type)
Allocate a size n array with structs or unions of the given type.
A 512-bit hashcode.
void GNUNET_SERVICE_client_drop(struct GNUNET_SERVICE_Client *c)
Ask the server to disconnect from the given client.
Definition: service.c:2315
struct GNUNET_TIME_AbsoluteNBO deadline
Until when should the decryption be finished?
struct DecryptPeerInfo * info
State information about other peers.
struct ClientState * cs
Which client is this for?
struct GNUNET_TIME_AbsoluteNBO start
Until when should the decryption start?
struct GNUNET_CONSENSUS_Handle * consensus
Handle to the consensus over partial decryptions.
unsigned int original_index
Original index in the key generation round.
struct GNUNET_TIME_Absolute deadline
When would we like the ciphertext to be decrypted?
struct GNUNET_SECRETSHARING_Ciphertext ciphertext
Ciphertext we want to decrypt.
struct GNUNET_SERVICE_Client * client
Client this is about.
#define GNUNET_log(kind,...)
void GNUNET_CONSENSUS_conclude(struct GNUNET_CONSENSUS_Handle *consensus, GNUNET_CONSENSUS_ConcludeCallback conclude, void *conclude_cls)
We are done with inserting new elements into the consensus; try to conclude the consensus within a gi...
static struct GNUNET_FS_DirScanner * ds
Handle to the directory scanner (for recursive insertions).
struct GNUNET_CONSENSUS_Handle * GNUNET_CONSENSUS_create(const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned int num_peers, const struct GNUNET_PeerIdentity *peers, const struct GNUNET_HashCode *session_id, struct GNUNET_TIME_Absolute start, struct GNUNET_TIME_Absolute deadline, GNUNET_CONSENSUS_ElementCallback new_element_cb, void *new_element_cls)
Create a consensus session.
struct GNUNET_TIME_Absolute start
When should we start communicating for decryption?
uint16_t num_peers
Peers that have the share.
void GNUNET_SERVICE_client_continue(struct GNUNET_SERVICE_Client *c)
Continue receiving further messages from the given client.
Definition: service.c:2234
Session to cooperatively decrypt a value.
Here is the call graph for this function:

◆ init_crypto_constants()

static void init_crypto_constants ( void  )
static

Definition at line 2192 of file gnunet-service-secretsharing.c.

References elgamal_g, elgamal_p, elgamal_q, GNUNET_assert, GNUNET_SECRETSHARING_ELGAMAL_G_HEX, GNUNET_SECRETSHARING_ELGAMAL_P_HEX, and GNUNET_SECRETSHARING_ELGAMAL_Q_HEX.

Referenced by run().

2193 {
2194  GNUNET_assert(0 == gcry_mpi_scan(&elgamal_q, GCRYMPI_FMT_HEX,
2196  GNUNET_assert(0 == gcry_mpi_scan(&elgamal_p, GCRYMPI_FMT_HEX,
2198  GNUNET_assert(0 == gcry_mpi_scan(&elgamal_g, GCRYMPI_FMT_HEX,
2200 }
#define GNUNET_SECRETSHARING_ELGAMAL_G_HEX
The g-parameter for ElGamal encryption, a generator of the unique size q subgroup of Z_p^*...
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
#define GNUNET_SECRETSHARING_ELGAMAL_Q_HEX
The q-parameter for ElGamal encryption, a 1023-bit Sophie Germain prime, q = (p-1)/2.
#define GNUNET_SECRETSHARING_ELGAMAL_P_HEX
The q-parameter for ElGamal encryption, a 1024-bit safe prime.
static gcry_mpi_t elgamal_g
Generator for prime field of order &#39;elgamal_q&#39;.
static gcry_mpi_t elgamal_p
Modulus of the prime field used for ElGamal.
static gcry_mpi_t elgamal_q
The ElGamal prime field order as libgcrypt mpi.
Here is the caller graph for this function:

◆ run()

static void run ( void *  cls,
const struct GNUNET_CONFIGURATION_Handle c,
struct GNUNET_SERVICE_Handle service 
)
static

Initialize secretsharing service.

Parameters
clsclosure
cconfiguration to use
servicethe initialized service

Definition at line 2211 of file gnunet-service-secretsharing.c.

References cleanup_task(), GNUNET_break, GNUNET_CRYPTO_eddsa_key_create_from_configuration(), GNUNET_CRYPTO_get_peer_identity(), GNUNET_ERROR_TYPE_ERROR, GNUNET_log, GNUNET_OK, GNUNET_SCHEDULER_add_shutdown(), GNUNET_SCHEDULER_shutdown(), init_crypto_constants(), and my_peer.

Referenced by client_disconnect_cb().

2214 {
2215  cfg = c;
2217  if (NULL == my_peer_private_key)
2218  {
2220  "could not access host private key\n");
2221  GNUNET_break(0);
2223  return;
2224  }
2226  if (GNUNET_OK !=
2228  &my_peer))
2229  {
2231  "could not retrieve host identity\n");
2232  GNUNET_break(0);
2234  return;
2235  }
2237  NULL);
2238 }
static const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration of this service.
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_shutdown(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run on shutdown, that is when a CTRL-C signal is received, or when GNUNET_SCHEDULER_shutdown() is being invoked.
Definition: scheduler.c:1284
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
static void init_crypto_constants(void)
void GNUNET_SCHEDULER_shutdown(void)
Request the shutdown of a scheduler.
Definition: scheduler.c:517
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
static struct GNUNET_PeerIdentity my_peer
Peer that runs this service.
static struct GNUNET_CRYPTO_EddsaPrivateKey * my_peer_private_key
Peer that runs this service.
#define GNUNET_log(kind,...)
int GNUNET_CRYPTO_get_peer_identity(const struct GNUNET_CONFIGURATION_Handle *cfg, struct GNUNET_PeerIdentity *dst)
Retrieve the identity of the host&#39;s peer.
struct GNUNET_CRYPTO_EddsaPrivateKey * GNUNET_CRYPTO_eddsa_key_create_from_configuration(const struct GNUNET_CONFIGURATION_Handle *cfg)
Create a new private key by reading our peer&#39;s key from the file specified in the configuration...
static void cleanup_task(void *cls)
Task run during shutdown.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ client_connect_cb()

static void* client_connect_cb ( void *  cls,
struct GNUNET_SERVICE_Client c,
struct GNUNET_MQ_Handle mq 
)
static

Callback called when a client connects to the service.

Parameters
clsclosure for the service
cthe new client that connected to the service
mqthe message queue used to send messages to the client
Returns
c

Definition at line 2250 of file gnunet-service-secretsharing.c.

References ClientState::client, GNUNET_new, mq, and ClientState::mq.

Referenced by client_disconnect_cb().

2253 {
2254  struct ClientState *cs = GNUNET_new(struct ClientState);;
2255 
2256  cs->client = c;
2257  cs->mq = mq;
2258  return cs;
2259 }
State we keep per client.
struct GNUNET_MQ_Handle * mq
MQ to talk to client.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
struct GNUNET_SERVICE_Client * client
Client this is about.
struct GNUNET_MQ_Handle * mq
Definition: 003.c:5
Here is the caller graph for this function:

◆ client_disconnect_cb()

static void client_disconnect_cb ( void *  cls,
struct GNUNET_SERVICE_Client c,
void *  internal_cls 
)
static

Callback called when a client disconnected from the service.

Parameters
clsclosure for the service
cthe client that disconnected
internal_clsshould be equal to c

Definition at line 2270 of file gnunet-service-secretsharing.c.

References client_connect_cb(), ClientState::decrypt_session, decrypt_session_destroy(), GNUNET_free, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE, GNUNET_MQ_handler_end, GNUNET_MQ_hd_var_size, GNUNET_SERVICE_MAIN(), GNUNET_SERVICE_OPTION_NONE, ClientState::keygen_session, keygen_session_destroy(), and run().

2273 {
2274  struct ClientState *cs = internal_cls;
2275 
2276  if (NULL != cs->keygen_session)
2278 
2279  if (NULL != cs->decrypt_session)
2281  GNUNET_free(cs);
2282 }
State we keep per client.
static void decrypt_session_destroy(struct DecryptSession *ds)
Destroy a decrypt session, removing it from the linked list of decrypt sessions.
struct DecryptSession * decrypt_session
Decrypt session of the client, if any.
static void keygen_session_destroy(struct KeygenSession *ks)
struct KeygenSession * keygen_session
Keygen session of the client, if any.
#define GNUNET_free(ptr)
Wrapper around free.
Here is the call graph for this function:

◆ GNUNET_SERVICE_MAIN()

GNUNET_SERVICE_MAIN ( "secretsharing"  ,
GNUNET_SERVICE_OPTION_NONE  ,
run,
client_connect_cb,
client_disconnect_cb,
NULL  ,
GNUNET_MQ_hd_var_size(client_keygen, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_GENERATE, struct GNUNET_SECRETSHARING_CreateMessage, NULL)  ,
GNUNET_MQ_hd_var_size(client_decrypt, GNUNET_MESSAGE_TYPE_SECRETSHARING_CLIENT_DECRYPT, struct GNUNET_SECRETSHARING_DecryptRequestMessage, NULL)  ,
GNUNET_MQ_handler_end()   
)

Define "main" method using service macro.

Referenced by client_disconnect_cb().

Here is the caller graph for this function:

Variable Documentation

◆ elgamal_q

gcry_mpi_t elgamal_q
static

◆ elgamal_p

gcry_mpi_t elgamal_p
static

◆ elgamal_g

gcry_mpi_t elgamal_g
static

◆ my_peer

struct GNUNET_PeerIdentity my_peer
static

◆ my_peer_private_key

struct GNUNET_CRYPTO_EddsaPrivateKey* my_peer_private_key
static

Peer that runs this service.

Definition at line 304 of file gnunet-service-secretsharing.c.

◆ cfg

const struct GNUNET_CONFIGURATION_Handle* cfg
static

Configuration of this service.

Definition at line 309 of file gnunet-service-secretsharing.c.