GNUnet 0.22.2
hello-uri.c File Reference

helper library for handling URI-based HELLOs More...

#include "platform.h"
#include "gnunet_util_lib.h"
#include "gnunet_signatures.h"
#include "gnunet_hello_uri_lib.h"
#include "gnunet_protocols.h"
Include dependency graph for hello-uri.c:

Go to the source code of this file.

Data Structures

struct  SignedAddress
 Binary block we sign when we sign an address. More...
 
struct  HelloSignaturePurpose
 Message signed as part of a HELLO block/URL. More...
 
struct  HelloUriMessage
 Message used when gossiping HELLOs between peers. More...
 
struct  BlockHeader
 Start of a 'block'. More...
 
struct  DhtHelloMessage
 Message used when a DHT provides its HELLO to direct neighbours. More...
 
struct  Address
 Address of a peer. More...
 
struct  GNUNET_HELLO_Builder
 Context for building (or parsing) HELLO URIs. More...
 
struct  AddressUriMergeResult
 Struct to wrap data to do the merge of to hello uris. More...
 
struct  GNUNET_HELLO_Parser
 Context for parsing HELLOs. More...
 

Functions

static void hash_addresses (const struct Address *a_head, struct GNUNET_HashCode *hash)
 Compute hash over addresses in builder. More...
 
static void sign_hello (const struct GNUNET_HELLO_Builder *builder, struct GNUNET_TIME_Absolute et, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_CRYPTO_EddsaSignature *sig)
 Create HELLO signature. More...
 
static enum GNUNET_GenericReturnValue verify_hello (const struct GNUNET_HELLO_Parser *parser, struct GNUNET_TIME_Absolute et, const struct GNUNET_CRYPTO_EddsaSignature *sig)
 Verify HELLO signature. More...
 
static struct GNUNET_HELLO_Parserparser_new (const struct GNUNET_PeerIdentity *pid)
 
struct GNUNET_HELLO_BuilderGNUNET_HELLO_builder_new (const struct GNUNET_PeerIdentity *pid)
 Allocate builder. More...
 
const struct GNUNET_PeerIdentityGNUNET_HELLO_parser_get_id (const struct GNUNET_HELLO_Parser *parser)
 Get the PeerIdentity for this builder. More...
 
struct GNUNET_HELLO_BuilderGNUNET_HELLO_builder_from_parser (const struct GNUNET_HELLO_Parser *p)
 Allocate builder from parser. More...
 
void GNUNET_HELLO_parser_free (struct GNUNET_HELLO_Parser *parser)
 Release resources of a builder. More...
 
void GNUNET_HELLO_builder_free (struct GNUNET_HELLO_Builder *builder)
 Release resources of a builder. More...
 
struct GNUNET_HELLO_ParserGNUNET_HELLO_parser_from_msg (const struct GNUNET_MessageHeader *msg)
 Parse msg. More...
 
static enum GNUNET_GenericReturnValue check_address (const char *address)
 
static enum GNUNET_GenericReturnValue parser_add_address (struct GNUNET_HELLO_Parser *parser, const char *address)
 
struct GNUNET_HELLO_ParserGNUNET_HELLO_parser_from_block (const void *block, size_t block_size)
 Parse block. More...
 
struct GNUNET_TIME_Absolute GNUNET_HELLO_get_expiration_time_from_msg (const struct GNUNET_MessageHeader *msg)
 Get the expiration time for this HELLO. More...
 
enum GNUNET_GenericReturnValue GNUNET_HELLO_builder_add_address (struct GNUNET_HELLO_Builder *builder, const char *address)
 Add individual address to the builder. More...
 
struct GNUNET_HELLO_ParserGNUNET_HELLO_parser_from_url (const char *url)
 Parse GNUnet HELLO url. More...
 
struct GNUNET_MessageHeaderGNUNET_HELLO_builder_to_dht_hello_msg (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_TIME_Relative expiration_time)
 Generate DHT HELLO message (without peer ID) from a builder. More...
 
char * GNUNET_HELLO_builder_to_url2 (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_TIME_Relative validity)
 Generate GNUnet HELLO URI from a builder. More...
 
char * GNUNET_HELLO_parser_to_url (const struct GNUNET_HELLO_Parser *parser)
 Generate GNUnet HELLO URI from a parser. More...
 
char * GNUNET_HELLO_builder_to_url (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv)
 Generate GNUnet HELLO URI from a builder. More...
 
enum GNUNET_GenericReturnValue GNUNET_HELLO_builder_to_block (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, void *block, size_t *block_size, struct GNUNET_TIME_Relative expiration_time)
 Generate DHT block from a builder. More...
 
enum GNUNET_GenericReturnValue GNUNET_HELLO_parser_to_block (const struct GNUNET_HELLO_Parser *parser, void *block, size_t *block_size)
 Generate DHT block from a parser. More...
 
struct GNUNET_MQ_EnvelopeGNUNET_HELLO_parser_to_env (const struct GNUNET_HELLO_Parser *parser)
 Generate envelope with GNUnet HELLO message (including peer ID) from a parser. More...
 
static struct GNUNET_MQ_EnvelopeGNUNET_HELLO_builder_to_env_ (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_TIME_Relative expiration_time, const struct GNUNET_CRYPTO_EddsaSignature *sig)
 
struct GNUNET_MQ_EnvelopeGNUNET_HELLO_builder_to_env (const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_TIME_Relative expiration_time)
 Generate envelope with GNUnet HELLO message (including peer ID) from a builder. More...
 
enum GNUNET_GenericReturnValue GNUNET_HELLO_builder_del_address (struct GNUNET_HELLO_Builder *builder, const char *address)
 Remove individual address from the builder. More...
 
const struct GNUNET_PeerIdentityGNUNET_HELLO_parser_iterate (const struct GNUNET_HELLO_Parser *parser, GNUNET_HELLO_UriCallback uc, void *uc_cls)
 Iterate over URIs in a parser. More...
 
enum GNUNET_GenericReturnValue GNUNET_HELLO_dht_msg_to_block (const struct GNUNET_MessageHeader *hello, const struct GNUNET_PeerIdentity *pid, void **block, size_t *block_size, struct GNUNET_TIME_Absolute *block_expiration)
 Convert a DHT hello message to a HELLO block. More...
 
char * GNUNET_HELLO_address_to_prefix (const char *address)
 Given an address as a string, extract the prefix that identifies the communicator offering transmissions to that address. More...
 
void GNUNET_HELLO_sign_address (const char *address, enum GNUNET_NetworkType nt, struct GNUNET_TIME_Absolute mono_time, const struct GNUNET_CRYPTO_EddsaPrivateKey *private_key, void **result, size_t *result_size)
 Build address record by signing raw information with private key. More...
 

Detailed Description

helper library for handling URI-based HELLOs

Author
Christian Grothoff

Note:

  • Current API does not support deserializing HELLO of another peer and then serializing it into another format (we always require the private key). Not sure if we need this, but if we do, we need to extend the builder and the API.
  • Current API does not allow overriding the default HELLO expiration time. We may want to add a function that does this to create bootstrap HELLOs shipped with the TGZ.

Definition in file hello-uri.c.

Function Documentation

◆ hash_addresses()

static void hash_addresses ( const struct Address a_head,
struct GNUNET_HashCode hash 
)
static

Compute hash over addresses in builder.

Parameters
builderthe builder to hash addresses of
[out]hashwhere to write the hash

Definition at line 297 of file hello-uri.c.

299{
300 struct GNUNET_HashContext *hc;
301
303 for (const struct Address *a = a_head;
304 NULL != a;
305 a = a->next)
306 {
308 "Hashing over %.*s\n",
309 (int) a->uri_len,
310 a->uri);
312 a->uri,
313 a->uri_len);
314 }
316 hash);
317
318}
static struct MyAddress * a_head
Head of addresses of this peer.
#define GNUNET_log(kind,...)
void GNUNET_CRYPTO_hash_context_read(struct GNUNET_HashContext *hc, const void *buf, size_t size)
Add data to be hashed.
Definition: crypto_hash.c:363
void GNUNET_CRYPTO_hash_context_finish(struct GNUNET_HashContext *hc, struct GNUNET_HashCode *r_hash)
Finish the hash computation.
Definition: crypto_hash.c:387
struct GNUNET_HashContext * GNUNET_CRYPTO_hash_context_start(void)
Start incremental hashing operation.
Definition: crypto_hash.c:347
@ GNUNET_ERROR_TYPE_DEBUG
Address of a peer.
Definition: hello-uri.c:178
struct MyAddress * next
Kept in a DLL.

References a_head, GNUNET_CRYPTO_hash_context_finish(), GNUNET_CRYPTO_hash_context_read(), GNUNET_CRYPTO_hash_context_start(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, and MyAddress::next.

Referenced by sign_hello(), and verify_hello().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ sign_hello()

static void sign_hello ( const struct GNUNET_HELLO_Builder builder,
struct GNUNET_TIME_Absolute  et,
const struct GNUNET_CRYPTO_EddsaPrivateKey priv,
struct GNUNET_CRYPTO_EddsaSignature sig 
)
static

Create HELLO signature.

Parameters
builderthe builder to use
etexpiration time to sign
privkey to sign with
[out]sigwhere to write the signature

Definition at line 330 of file hello-uri.c.

334{
335 struct HelloSignaturePurpose hsp = {
336 .purpose.size = htonl (sizeof (hsp)),
337 .purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_HELLO),
338 .expiration_time = GNUNET_TIME_absolute_hton (et)
339 };
340
341 hash_addresses (builder->a_head,
342 &hsp.h_addrs);
344 "Address hash is %s\n",
345 GNUNET_h2s_full (&hsp.h_addrs));
347 &hsp,
348 sig);
349}
static struct HostSet * builder
NULL if we are not currently iterating over peer information.
#define GNUNET_CRYPTO_eddsa_sign(priv, ps, sig)
EdDSA sign a given block.
const char * GNUNET_h2s_full(const struct GNUNET_HashCode *hc)
Convert a hash value to a string (for printing debug messages).
struct GNUNET_TIME_AbsoluteNBO GNUNET_TIME_absolute_hton(struct GNUNET_TIME_Absolute a)
Convert absolute time to network byte order.
Definition: time.c:640
static void hash_addresses(const struct Address *a_head, struct GNUNET_HashCode *hash)
Compute hash over addresses in builder.
Definition: hello-uri.c:297
#define GNUNET_SIGNATURE_PURPOSE_HELLO
Signature by which a peer affirms its address.
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!...
Message signed as part of a HELLO block/URL.
Definition: hello-uri.c:71
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
Purpose must be GNUNET_SIGNATURE_PURPOSE_HELLO.
Definition: hello-uri.c:75
struct GNUNET_HashCode h_addrs
Hash over all addresses.
Definition: hello-uri.c:85

References builder, GNUNET_CRYPTO_eddsa_sign, GNUNET_ERROR_TYPE_DEBUG, GNUNET_h2s_full(), GNUNET_log, GNUNET_SIGNATURE_PURPOSE_HELLO, GNUNET_TIME_absolute_hton(), HelloSignaturePurpose::h_addrs, hash_addresses(), HelloSignaturePurpose::purpose, and GNUNET_CRYPTO_EccSignaturePurpose::size.

Referenced by GNUNET_HELLO_builder_to_block(), and GNUNET_HELLO_builder_to_url2().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ verify_hello()

static enum GNUNET_GenericReturnValue verify_hello ( const struct GNUNET_HELLO_Parser parser,
struct GNUNET_TIME_Absolute  et,
const struct GNUNET_CRYPTO_EddsaSignature sig 
)
static

Verify HELLO signature.

Parameters
builderthe builder to use
etexpiration time to verify
sigsignature to verify
Returns
GNUNET_OK if everything is ok, GNUNET_NO if the HELLO expired, GNUNET_SYSERR if the signature is wrong

Definition at line 362 of file hello-uri.c.

365{
366 struct HelloSignaturePurpose hsp = {
367 .purpose.size = htonl (sizeof (hsp)),
368 .purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_HELLO),
369 .expiration_time = GNUNET_TIME_absolute_hton (et)
370 };
371
372 hash_addresses (parser->a_head,
373 &hsp.h_addrs);
374 if (GNUNET_OK !=
376 &hsp,
377 sig,
378 &parser->pid.public_key))
379 {
380 GNUNET_break_op (0);
381 return GNUNET_SYSERR;
382 }
384 return GNUNET_NO;
385 return GNUNET_OK;
386}
#define GNUNET_CRYPTO_eddsa_verify(purp, ps, sig, pub)
Verify EdDSA signature.
@ GNUNET_OK
@ GNUNET_NO
@ GNUNET_SYSERR
#define GNUNET_break_op(cond)
Use this for assertion violations caused by other peers (i.e.
bool GNUNET_TIME_absolute_is_past(struct GNUNET_TIME_Absolute abs)
Test if abs is truly in the past (excluding now).
Definition: time.c:671

References GNUNET_break_op, GNUNET_CRYPTO_eddsa_verify, GNUNET_NO, GNUNET_OK, GNUNET_SIGNATURE_PURPOSE_HELLO, GNUNET_SYSERR, GNUNET_TIME_absolute_hton(), GNUNET_TIME_absolute_is_past(), HelloSignaturePurpose::h_addrs, hash_addresses(), consensus-simulation::parser, HelloSignaturePurpose::purpose, and GNUNET_CRYPTO_EccSignaturePurpose::size.

Referenced by GNUNET_HELLO_dht_msg_to_block(), GNUNET_HELLO_parser_from_block(), and GNUNET_HELLO_parser_from_url().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ parser_new()

static struct GNUNET_HELLO_Parser * parser_new ( const struct GNUNET_PeerIdentity pid)
static

Definition at line 390 of file hello-uri.c.

391{
392 struct GNUNET_HELLO_Parser *p;
393
395 p->pid = *pid;
396 return p;
397}
static struct GNUNET_PeerIdentity pid
Identity of the peer we transmit to / connect to.
static struct GNUNET_OS_Process * p
Helper process we started.
Definition: gnunet-uri.c:38
#define GNUNET_new(type)
Allocate a struct or union of the given type.
Context for parsing HELLOs.
Definition: hello-uri.c:258
pid_t pid
PID of the process.
Definition: os_priority.c:49

References GNUNET_new, p, GNUNET_OS_Process::pid, and pid.

Referenced by GNUNET_HELLO_parser_from_block(), and GNUNET_HELLO_parser_from_url().

Here is the caller graph for this function:

◆ check_address()

static enum GNUNET_GenericReturnValue check_address ( const char *  address)
static

Definition at line 494 of file hello-uri.c.

495{
496 const char *e;
497
498 if (NULL == (e = strstr (address,
499 "://")))
500 {
501 GNUNET_break_op (0);
503 "Invalid address `%s'\n",
504 address);
505 return GNUNET_SYSERR;
506 }
507 if (e == address)
508 {
509 GNUNET_break_op (0);
510 return GNUNET_SYSERR;
511 }
512 for (const char *p = address; p != e; p++)
513 if ( (! isalpha ((unsigned char) *p)) &&
514 ('+' != *p) )
515 {
516 GNUNET_break_op (0);
517 return GNUNET_SYSERR;
518 }
519 return GNUNET_OK;
520}
static char * address
GNS address for this phone.
@ GNUNET_ERROR_TYPE_ERROR

References address, GNUNET_break_op, GNUNET_ERROR_TYPE_ERROR, GNUNET_log, GNUNET_OK, GNUNET_SYSERR, and p.

Referenced by GNUNET_HELLO_builder_add_address(), and parser_add_address().

Here is the caller graph for this function:

◆ parser_add_address()

static enum GNUNET_GenericReturnValue parser_add_address ( struct GNUNET_HELLO_Parser parser,
const char *  address 
)
static

Definition at line 523 of file hello-uri.c.

525{
526 struct Address *a;
528 size_t alen = strlen (address) + 1;
529
531 if (GNUNET_OK != ret)
532 {
534 "Failed to add address to builder\n");
535 return ret;
536 }
537 /* check for duplicates */
538 for (a = parser->a_head;
539 NULL != a;
540 a = a->next)
541 if (0 == strcmp (address,
542 a->uri))
543 return GNUNET_NO;
544 a = GNUNET_malloc (sizeof (struct Address) + alen);
545 a->uri_len = alen;
546 memcpy (&a[1],
547 address,
548 alen);
549 a->uri = (const char *) &a[1];
551 parser->a_tail,
552 a);
553 parser->a_length++;
554 return GNUNET_OK;
555}
static int ret
Final status code.
Definition: gnunet-arm.c:93
#define GNUNET_CONTAINER_DLL_insert_tail(head, tail, element)
Insert an element at the tail of a DLL.
GNUNET_GenericReturnValue
Named constants for return values.
#define GNUNET_malloc(size)
Wrapper around malloc.
static enum GNUNET_GenericReturnValue check_address(const char *address)
Definition: hello-uri.c:494
struct Address * next
Kept in a DLL.
Definition: hello-uri.c:182
size_t uri_len
Length of uri including 0-terminator.
Definition: hello-uri.c:197
const char * uri
Actual URI, allocated at the end of this struct.
Definition: hello-uri.c:192

References address, check_address(), GNUNET_CONTAINER_DLL_insert_tail, GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, GNUNET_malloc, GNUNET_NO, GNUNET_OK, Address::next, consensus-simulation::parser, ret, Address::uri, and Address::uri_len.

Referenced by GNUNET_HELLO_parser_from_block(), and GNUNET_HELLO_parser_from_url().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ GNUNET_HELLO_builder_to_env_()

static struct GNUNET_MQ_Envelope * GNUNET_HELLO_builder_to_env_ ( const struct GNUNET_HELLO_Builder builder,
const struct GNUNET_CRYPTO_EddsaPrivateKey priv,
struct GNUNET_TIME_Relative  expiration_time,
const struct GNUNET_CRYPTO_EddsaSignature sig 
)
static

Definition at line 1132 of file hello-uri.c.

1136{
1137 struct GNUNET_MQ_Envelope *env;
1138 struct HelloUriMessage *msg;
1139 size_t blen;
1140
1141 if (builder->a_length > UINT16_MAX)
1142 {
1143 GNUNET_break (0);
1144 return NULL;
1145 }
1146 blen = 0;
1149 priv,
1150 NULL,
1151 &blen,
1152 expiration_time));
1154 blen,
1156 msg->url_counter = htons ((uint16_t) builder->a_length);
1159 priv,
1160 &msg[1],
1161 &blen,
1162 expiration_time));
1163 return env;
1164}
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
struct GNUNET_MQ_Envelope * env
Definition: 005.c:1
enum GNUNET_GenericReturnValue GNUNET_HELLO_builder_to_block(const struct GNUNET_HELLO_Builder *builder, const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, void *block, size_t *block_size, struct GNUNET_TIME_Relative expiration_time)
Generate DHT block from a builder.
Definition: hello-uri.c:1006
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur.
#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:61
#define GNUNET_MESSAGE_TYPE_HELLO_URI
Latest HELLO messages used for communicating peer addresses.
Message used when gossiping HELLOs between peers.
Definition: hello-uri.c:93

References builder, env, GNUNET_assert, GNUNET_break, GNUNET_HELLO_builder_to_block(), GNUNET_MESSAGE_TYPE_HELLO_URI, GNUNET_MQ_msg_extra, GNUNET_NO, GNUNET_OK, and msg.

Referenced by GNUNET_HELLO_builder_to_env().

Here is the call graph for this function:
Here is the caller graph for this function: