GNUnet  0.11.x
Data Structures | Macros | Functions
dht_api.c File Reference

library to access the DHT service More...

#include "platform.h"
#include "gnunet_util_lib.h"
#include "gnunet_constants.h"
#include "gnunet_arm_service.h"
#include "gnunet_hello_lib.h"
#include "gnunet_protocols.h"
#include "gnunet_dht_service.h"
#include "dht.h"
Include dependency graph for dht_api.c:

Go to the source code of this file.

Data Structures

struct  GNUNET_DHT_PutHandle
 Handle to a PUT request. More...
 
struct  GNUNET_DHT_GetHandle
 Handle to a GET request. More...
 
struct  GNUNET_DHT_MonitorHandle
 Handle to a monitoring request. More...
 
struct  GNUNET_DHT_Handle
 Connection to the DHT service. More...
 

Macros

#define LOG(kind, ...)   GNUNET_log_from (kind, "dht-api", __VA_ARGS__)
 

Functions

static int try_connect (struct GNUNET_DHT_Handle *h)
 Try to (re)connect to the DHT service. More...
 
static void send_get (struct GNUNET_DHT_GetHandle *gh)
 Send GET message for a get_handle to DHT. More...
 
static void send_get_known_results (struct GNUNET_DHT_GetHandle *gh, unsigned int transmission_offset_start)
 Send GET message(s) for indicating which results are already known for a get_handle to DHT. More...
 
static int add_get_request_to_pending (void *cls, const struct GNUNET_HashCode *key, void *value)
 Add the GET request corresponding to the given route handle to the pending queue (if it is not already in there). More...
 
static void send_monitor_start (struct GNUNET_DHT_MonitorHandle *mh)
 Send GNUNET_MESSAGE_TYPE_DHT_MONITOR_START message. More...
 
static void try_reconnect (void *cls)
 Try reconnecting to the dht service. More...
 
static void do_disconnect (struct GNUNET_DHT_Handle *h)
 Try reconnecting to the DHT service. More...
 
static void mq_error_handler (void *cls, enum GNUNET_MQ_Error error)
 Generic error handler, called with the appropriate error code and the same closure specified at the creation of the message queue. More...
 
static int check_monitor_get (void *cls, const struct GNUNET_DHT_MonitorGetMessage *msg)
 Verify integrity of a get monitor message from the service. More...
 
static void handle_monitor_get (void *cls, const struct GNUNET_DHT_MonitorGetMessage *msg)
 Process a get monitor message from the service. More...
 
static int check_monitor_get_resp (void *cls, const struct GNUNET_DHT_MonitorGetRespMessage *msg)
 Validate a get response monitor message from the service. More...
 
static void handle_monitor_get_resp (void *cls, const struct GNUNET_DHT_MonitorGetRespMessage *msg)
 Process a get response monitor message from the service. More...
 
static int check_monitor_put (void *cls, const struct GNUNET_DHT_MonitorPutMessage *msg)
 Check validity of a put monitor message from the service. More...
 
static void handle_monitor_put (void *cls, const struct GNUNET_DHT_MonitorPutMessage *msg)
 Process a put monitor message from the service. More...
 
static int check_client_result (void *cls, const struct GNUNET_DHT_ClientResultMessage *msg)
 Verify that client result message received from the service is well-formed. More...
 
static int process_client_result (void *cls, const struct GNUNET_HashCode *key, void *value)
 Process a given reply that might match the given request. More...
 
static void handle_client_result (void *cls, const struct GNUNET_DHT_ClientResultMessage *msg)
 Process a client result message received from the service. More...
 
static void handle_put_cont (void *cls)
 Process a MQ PUT transmission notification. More...
 
struct GNUNET_DHT_HandleGNUNET_DHT_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned int ht_len)
 Initialize the connection with the DHT service. More...
 
void GNUNET_DHT_disconnect (struct GNUNET_DHT_Handle *handle)
 Shutdown connection with the DHT service. More...
 
struct GNUNET_DHT_PutHandleGNUNET_DHT_put (struct GNUNET_DHT_Handle *handle, const struct GNUNET_HashCode *key, uint32_t desired_replication_level, enum GNUNET_DHT_RouteOption options, enum GNUNET_BLOCK_Type type, size_t size, const void *data, struct GNUNET_TIME_Absolute exp, GNUNET_SCHEDULER_TaskCallback cont, void *cont_cls)
 Perform a PUT operation storing data in the DHT. More...
 
void GNUNET_DHT_put_cancel (struct GNUNET_DHT_PutHandle *ph)
 Cancels a DHT PUT operation. More...
 
struct GNUNET_DHT_GetHandleGNUNET_DHT_get_start (struct GNUNET_DHT_Handle *handle, enum GNUNET_BLOCK_Type type, const struct GNUNET_HashCode *key, uint32_t desired_replication_level, enum GNUNET_DHT_RouteOption options, const void *xquery, size_t xquery_size, GNUNET_DHT_GetIterator iter, void *iter_cls)
 Perform an asynchronous GET operation on the DHT identified. More...
 
void GNUNET_DHT_get_filter_known_results (struct GNUNET_DHT_GetHandle *get_handle, unsigned int num_results, const struct GNUNET_HashCode *results)
 Tell the DHT not to return any of the following known results to this client. More...
 
void GNUNET_DHT_get_stop (struct GNUNET_DHT_GetHandle *get_handle)
 Stop async DHT-get. More...
 
struct GNUNET_DHT_MonitorHandleGNUNET_DHT_monitor_start (struct GNUNET_DHT_Handle *handle, enum GNUNET_BLOCK_Type type, const struct GNUNET_HashCode *key, GNUNET_DHT_MonitorGetCB get_cb, GNUNET_DHT_MonitorGetRespCB get_resp_cb, GNUNET_DHT_MonitorPutCB put_cb, void *cb_cls)
 Start monitoring the local DHT service. More...
 
void GNUNET_DHT_monitor_stop (struct GNUNET_DHT_MonitorHandle *mh)
 Stop monitoring. More...
 

Detailed Description

library to access the DHT service

Author
Christian Grothoff
Nathan Evans

Definition in file dht_api.c.

Macro Definition Documentation

◆ LOG

#define LOG (   kind,
  ... 
)    GNUNET_log_from (kind, "dht-api", __VA_ARGS__)

Definition at line 37 of file dht_api.c.

Function Documentation

◆ try_connect()

static int try_connect ( struct GNUNET_DHT_Handle h)
static

Try to (re)connect to the DHT service.

Parameters
hDHT handle to reconnect
Returns
GNUNET_YES on success, GNUNET_NO on failure.

Definition at line 842 of file dht_api.c.

843 {
845  GNUNET_MQ_hd_var_size (monitor_get,
848  h),
849  GNUNET_MQ_hd_var_size (monitor_get_resp,
852  h),
853  GNUNET_MQ_hd_var_size (monitor_put,
856  h),
857  GNUNET_MQ_hd_var_size (client_result,
860  h),
862  };
863 
864  if (NULL != h->mq)
865  return GNUNET_OK;
867  "dht",
868  handlers,
870  h);
871  if (NULL == h->mq)
872  {
874  "Failed to connect to the DHT service!\n");
875  return GNUNET_NO;
876  }
877  return GNUNET_YES;
878 }
static void mq_error_handler(void *cls, enum GNUNET_MQ_Error error)
Generic error handler, called with the appropriate error code and the same closure specified at the c...
Definition: dht_api.c:474
#define LOG(kind,...)
Definition: dht_api.c:37
static struct GNUNET_ARM_Handle * h
Connection with ARM.
Definition: gnunet-arm.c:99
static struct GNUNET_CADET_MessageHandler handlers[]
Handlers, for diverse services.
@ GNUNET_OK
Definition: gnunet_common.h:95
@ GNUNET_YES
Definition: gnunet_common.h:97
@ GNUNET_NO
Definition: gnunet_common.h:94
struct GNUNET_MQ_Handle * GNUNET_CLIENT_connect(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *service_name, const struct GNUNET_MQ_MessageHandler *handlers, GNUNET_MQ_ErrorHandler error_handler, void *error_handler_cls)
Create a message queue to connect to a GNUnet service.
Definition: client.c:1064
@ GNUNET_ERROR_TYPE_WARNING
#define GNUNET_MQ_handler_end()
End-marker for the handlers array.
#define GNUNET_MQ_hd_var_size(name, code, str, ctx)
#define GNUNET_MESSAGE_TYPE_DHT_MONITOR_GET
Receive information about transiting GETs.
#define GNUNET_MESSAGE_TYPE_DHT_MONITOR_GET_RESP
Receive information about transiting GET responses.
#define GNUNET_MESSAGE_TYPE_DHT_MONITOR_PUT
Receive information about transiting PUTs.
#define GNUNET_MESSAGE_TYPE_DHT_CLIENT_RESULT
Service returns result to client.
struct GNUNET_MQ_Handle * mq
Our connection to the ARM service.
Definition: arm_api.c:107
const struct GNUNET_CONFIGURATION_Handle * cfg
The configuration that we are using.
Definition: arm_api.c:112
Reply to a GET send from the service to a client.
Definition: dht.h:144
Message to monitor get requests going through peer, DHT service -> clients.
Definition: dht.h:324
Message to monitor get results going through peer, DHT service -> clients.
Definition: dht.h:368
Message to monitor put requests going through peer, DHT service -> clients.
Definition: dht.h:229
Message handler for a specific message type.

References GNUNET_ARM_Handle::cfg, GNUNET_CLIENT_connect(), GNUNET_ERROR_TYPE_WARNING, GNUNET_MESSAGE_TYPE_DHT_CLIENT_RESULT, GNUNET_MESSAGE_TYPE_DHT_MONITOR_GET, GNUNET_MESSAGE_TYPE_DHT_MONITOR_GET_RESP, GNUNET_MESSAGE_TYPE_DHT_MONITOR_PUT, GNUNET_MQ_handler_end, GNUNET_MQ_hd_var_size, GNUNET_NO, GNUNET_OK, GNUNET_YES, h, handlers, LOG, GNUNET_ARM_Handle::mq, and mq_error_handler().

Referenced by GNUNET_DHT_connect(), and try_reconnect().

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

◆ send_get()

static void send_get ( struct GNUNET_DHT_GetHandle gh)
static

Send GET message for a get_handle to DHT.

Parameters
ghGET to generate messages for.

Definition at line 273 of file dht_api.c.

274 {
275  struct GNUNET_DHT_Handle *h = gh->dht_handle;
276  struct GNUNET_MQ_Envelope *env;
277  struct GNUNET_DHT_ClientGetMessage *get_msg;
278 
279  env = GNUNET_MQ_msg_extra (get_msg,
280  gh->xquery_size,
282  get_msg->options = htonl ((uint32_t) gh->options);
283  get_msg->desired_replication_level = htonl (gh->desired_replication_level);
284  get_msg->type = htonl (gh->type);
285  get_msg->key = gh->key;
286  get_msg->unique_id = gh->unique_id;
287  GNUNET_memcpy (&get_msg[1],
288  &gh[1],
289  gh->xquery_size);
290  GNUNET_MQ_send (h->mq,
291  env);
292 }
struct GNUNET_MQ_Envelope * env
Definition: 005.c:1
static struct GNUNET_TRANSPORT_HelloGetHandle * gh
Pending GNUNET_TRANSPORT_hello_get() operation.
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
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:355
#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
#define GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET
Client wants to lookup item in DHT.
DHT GET message sent from clients to service.
Definition: dht.h:72
uint64_t unique_id
Unique ID identifying this request, if 0 then the client will not expect a response.
Definition: dht.h:103
uint32_t options
Message options, actually an 'enum GNUNET_DHT_RouteOption' value.
Definition: dht.h:81
struct GNUNET_HashCode key
The key to search for.
Definition: dht.h:97
uint32_t type
The type for the data for the GET request; actually an 'enum GNUNET_BLOCK_Type'.
Definition: dht.h:92
uint32_t desired_replication_level
Replication level for this message.
Definition: dht.h:86
Connection to the DHT service.
Definition: dht_api.c:202

References GNUNET_DHT_ClientGetMessage::desired_replication_level, env, gh, GNUNET_memcpy, GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET, GNUNET_MQ_msg_extra, GNUNET_MQ_send(), h, GNUNET_DHT_ClientGetMessage::key, GNUNET_ARM_Handle::mq, GNUNET_DHT_ClientGetMessage::options, GNUNET_DHT_ClientGetMessage::type, and GNUNET_DHT_ClientGetMessage::unique_id.

Referenced by add_get_request_to_pending(), and GNUNET_DHT_get_start().

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

◆ send_get_known_results()

static void send_get_known_results ( struct GNUNET_DHT_GetHandle gh,
unsigned int  transmission_offset_start 
)
static

Send GET message(s) for indicating which results are already known for a get_handle to DHT.

Complex as we need to send the list of known results, which means we may need multiple messages to block known results from the result set.

Parameters
ghGET to generate messages for
transmission_offset_startat which offset should we start?

Definition at line 305 of file dht_api.c.

307 {
308  struct GNUNET_DHT_Handle *h = gh->dht_handle;
309  struct GNUNET_MQ_Envelope *env;
311  unsigned int delta;
312  unsigned int max;
313  unsigned int transmission_offset;
314 
315  max = (GNUNET_MAX_MESSAGE_SIZE - sizeof(*msg))
316  / sizeof(struct GNUNET_HashCode);
317  transmission_offset = transmission_offset_start;
318  while (transmission_offset < gh->seen_results_end)
319  {
320  delta = gh->seen_results_end - transmission_offset;
321  if (delta > max)
322  delta = max;
324  delta * sizeof(struct GNUNET_HashCode),
326  msg->key = gh->key;
327  msg->unique_id = gh->unique_id;
328  GNUNET_memcpy (&msg[1],
329  &gh->seen_results[transmission_offset],
330  sizeof(struct GNUNET_HashCode) * delta);
331  GNUNET_MQ_send (h->mq,
332  env);
333  transmission_offset += delta;
334  }
335 }
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
#define GNUNET_MAX_MESSAGE_SIZE
Largest supported message (to be precise, one byte more than the largest possible message,...
#define GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN
Certain results are already known to the client, filter those.
#define max(x, y)
static struct GNUNET_TIME_Relative delta
Definition: speedup.c:35
DHT GET RESULTS KNOWN message sent from clients to service.
Definition: dht.h:114
A 512-bit hashcode.

References delta, env, gh, GNUNET_MAX_MESSAGE_SIZE, GNUNET_memcpy, GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN, GNUNET_MQ_msg_extra, GNUNET_MQ_send(), h, max, GNUNET_ARM_Handle::mq, and msg.

Referenced by add_get_request_to_pending(), and GNUNET_DHT_get_filter_known_results().

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

◆ add_get_request_to_pending()

static int add_get_request_to_pending ( void *  cls,
const struct GNUNET_HashCode key,
void *  value 
)
static

Add the GET request corresponding to the given route handle to the pending queue (if it is not already in there).

Parameters
clsthe struct GNUNET_DHT_Handle *
keykey for the request (not used)
valuethe struct GNUNET_DHT_GetHandle *
Returns
GNUNET_YES (always)

Definition at line 348 of file dht_api.c.

351 {
352  struct GNUNET_DHT_Handle *handle = cls;
353  struct GNUNET_DHT_GetHandle *gh = value;
354 
356  "Retransmitting request related to %s to DHT %p\n",
357  GNUNET_h2s (key),
358  handle);
359  send_get (gh);
361  return GNUNET_YES;
362 }
static void send_get(struct GNUNET_DHT_GetHandle *gh)
Send GET message for a get_handle to DHT.
Definition: dht_api.c:273
static void send_get_known_results(struct GNUNET_DHT_GetHandle *gh, unsigned int transmission_offset_start)
Send GET message(s) for indicating which results are already known for a get_handle to DHT.
Definition: dht_api.c:305
struct GNUNET_HashCode key
The key used in the DHT.
static struct GNUNET_DNS_Handle * handle
Handle to transport service.
static char * value
Value of the record to add/remove.
const char * GNUNET_h2s(const struct GNUNET_HashCode *hc)
Convert a hash value to a string (for printing debug messages).
@ GNUNET_ERROR_TYPE_DEBUG
Handle to a GET request.
Definition: dht_api.c:80

References gh, GNUNET_ERROR_TYPE_DEBUG, GNUNET_h2s(), GNUNET_YES, handle, key, LOG, send_get(), send_get_known_results(), and value.

Referenced by try_reconnect().

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

◆ send_monitor_start()

static void send_monitor_start ( struct GNUNET_DHT_MonitorHandle mh)
static

Send GNUNET_MESSAGE_TYPE_DHT_MONITOR_START message.

Parameters
mhmonitor handle to generate start message for

Definition at line 371 of file dht_api.c.

372 {
373  struct GNUNET_DHT_Handle *h = mh->dht_handle;
374  struct GNUNET_MQ_Envelope *env;
376 
377  env = GNUNET_MQ_msg (m,
379  m->type = htonl (mh->type);
380  m->get = htons (NULL != mh->get_cb);
381  m->get_resp = htons (NULL != mh->get_resp_cb);
382  m->put = htons (NULL != mh->put_cb);
383  if (NULL != mh->key)
384  {
385  m->filter_key = htons (1);
386  m->key = *mh->key;
387  }
388  GNUNET_MQ_send (h->mq,
389  env);
390 }
static struct GNUNET_ARM_MonitorHandle * m
Monitor connection with ARM.
Definition: gnunet-arm.c:104
static struct GNUNET_CADET_Handle * mh
Cadet handle.
Definition: gnunet-cadet.c:92
#define GNUNET_MQ_msg(mvar, type)
Allocate a GNUNET_MQ_Envelope.
Definition: gnunet_mq_lib.h:67
#define GNUNET_MESSAGE_TYPE_DHT_MONITOR_START
Request information about transiting messages.
Message to request monitoring messages, clients -> DHT service.
Definition: dht.h:281

References env, GNUNET_MESSAGE_TYPE_DHT_MONITOR_START, GNUNET_MQ_msg, GNUNET_MQ_send(), h, m, mh, and GNUNET_ARM_Handle::mq.

Referenced by GNUNET_DHT_monitor_start(), and try_reconnect().

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

◆ try_reconnect()

static void try_reconnect ( void *  cls)
static

Try reconnecting to the dht service.

Parameters
clsa struct GNUNET_DHT_Handle

Definition at line 399 of file dht_api.c.

400 {
401  struct GNUNET_DHT_Handle *h = cls;
403 
405  "Reconnecting with DHT %p\n",
406  h);
407  h->retry_time = GNUNET_TIME_STD_BACKOFF (h->retry_time);
408  h->reconnect_task = NULL;
409  if (GNUNET_YES != try_connect (h))
410  {
412  "DHT reconnect failed!\n");
414  = GNUNET_SCHEDULER_add_delayed (h->retry_time,
415  &try_reconnect,
416  h);
417  return;
418  }
419  GNUNET_CONTAINER_multihashmap_iterate (h->active_requests,
421  h);
422  for (mh = h->monitor_head; NULL != mh; mh = mh->next)
424 }
static void try_reconnect(void *cls)
Try reconnecting to the dht service.
Definition: dht_api.c:399
static int add_get_request_to_pending(void *cls, const struct GNUNET_HashCode *key, void *value)
Add the GET request corresponding to the given route handle to the pending queue (if it is not alread...
Definition: dht_api.c:348
static int try_connect(struct GNUNET_DHT_Handle *h)
Try to (re)connect to the DHT service.
Definition: dht_api.c:842
static void send_monitor_start(struct GNUNET_DHT_MonitorHandle *mh)
Send GNUNET_MESSAGE_TYPE_DHT_MONITOR_START message.
Definition: dht_api.c:371
int GNUNET_CONTAINER_multihashmap_iterate(struct GNUNET_CONTAINER_MultiHashMap *map, GNUNET_CONTAINER_MulitHashMapIteratorCallback it, void *it_cls)
Iterate over all entries in the map.
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_delayed(struct GNUNET_TIME_Relative delay, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay.
Definition: scheduler.c:1269
#define GNUNET_TIME_STD_BACKOFF(r)
Perform our standard exponential back-off calculation, starting at 1 ms and then going by a factor of...
struct GNUNET_SCHEDULER_Task * reconnect_task
ID of the reconnect task (if any).
Definition: arm_api.c:147
Handle to a monitoring request.
Definition: dht_api.c:150

References add_get_request_to_pending(), GNUNET_CONTAINER_multihashmap_iterate(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_WARNING, GNUNET_SCHEDULER_add_delayed(), GNUNET_TIME_STD_BACKOFF, GNUNET_YES, h, LOG, mh, GNUNET_ARM_Handle::reconnect_task, send_monitor_start(), and try_connect().

Referenced by do_disconnect().

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

◆ do_disconnect()

static void do_disconnect ( struct GNUNET_DHT_Handle h)
static

Try reconnecting to the DHT service.

Parameters
hhandle to dht to (possibly) disconnect and reconnect

Definition at line 433 of file dht_api.c.

434 {
435  struct GNUNET_DHT_PutHandle *ph;
437  void *cont_cls;
438 
439  if (NULL == h->mq)
440  return;
442  h->mq = NULL;
444  "Disconnecting from DHT service, will try to reconnect in %s\n",
446  GNUNET_YES));
447  /* notify client about all PUTs that (may) have failed due to disconnect */
448  while (NULL != (ph = h->put_head))
449  {
450  cont = ph->cont;
451  cont_cls = ph->cont_cls;
452  ph->env = NULL;
454  if (NULL != cont)
455  cont (cont_cls);
456  }
457  GNUNET_assert (NULL == h->reconnect_task);
459  = GNUNET_SCHEDULER_add_delayed (h->retry_time,
460  &try_reconnect,
461  h);
462 }
static struct GNUNET_ATS_PerformanceHandle * ph
ATS performance handle used.
Definition: gnunet-ats.c:116
#define GNUNET_log(kind,...)
void GNUNET_DHT_put_cancel(struct GNUNET_DHT_PutHandle *ph)
Cancels a DHT PUT operation.
Definition: dht_api.c:1035
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
void GNUNET_MQ_destroy(struct GNUNET_MQ_Handle *mq)
Destroy the message queue.
Definition: mq.c:837
void(* GNUNET_SCHEDULER_TaskCallback)(void *cls)
Signature of the main function of a task.
const char * GNUNET_STRINGS_relative_time_to_string(struct GNUNET_TIME_Relative delta, int do_round)
Give relative time in human-readable fancy format.
Definition: strings.c:557
Handle to a PUT request.
Definition: dht_api.c:44
void * cont_cls
Closure for cont.
Definition: dht_api.c:68
GNUNET_SCHEDULER_TaskCallback cont
Continuation to call when done.
Definition: dht_api.c:58

References GNUNET_DHT_PutHandle::cont, GNUNET_DHT_PutHandle::cont_cls, GNUNET_assert, GNUNET_DHT_put_cancel(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, GNUNET_MQ_destroy(), GNUNET_SCHEDULER_add_delayed(), GNUNET_STRINGS_relative_time_to_string(), GNUNET_YES, h, GNUNET_ARM_Handle::mq, ph, GNUNET_ARM_Handle::reconnect_task, and try_reconnect().

Referenced by mq_error_handler().

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

◆ mq_error_handler()

static void mq_error_handler ( void *  cls,
enum GNUNET_MQ_Error  error 
)
static

Generic error handler, called with the appropriate error code and the same closure specified at the creation of the message queue.

Not every message queue implementation supports an error handler.

Parameters
clsclosure with the struct GNUNET_DHT_Handle *
errorerror code

Definition at line 474 of file dht_api.c.

476 {
477  struct GNUNET_DHT_Handle *h = cls;
478 
479  do_disconnect (h);
480 }
static void do_disconnect(struct GNUNET_DHT_Handle *h)
Try reconnecting to the DHT service.
Definition: dht_api.c:433

References do_disconnect(), and h.

Referenced by try_connect().

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

◆ check_monitor_get()

static int check_monitor_get ( void *  cls,
const struct GNUNET_DHT_MonitorGetMessage msg 
)
static

Verify integrity of a get monitor message from the service.

Parameters
clsThe DHT handle.
msgMonitor get message from the service.
Returns
GNUNET_OK if everything went fine, GNUNET_SYSERR if the message is malformed.

Definition at line 492 of file dht_api.c.

494 {
495  uint32_t plen = ntohl (msg->get_path_length);
496  uint16_t msize = ntohs (msg->header.size) - sizeof(*msg);
497 
498  if ((plen > UINT16_MAX) ||
499  (plen * sizeof(struct GNUNET_PeerIdentity) != msize))
500  {
501  GNUNET_break (0);
502  return GNUNET_SYSERR;
503  }
504  return GNUNET_OK;
505 }
@ GNUNET_SYSERR
Definition: gnunet_common.h:93
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format.
The identity of the host (wraps the signing key of the peer).

References GNUNET_break, GNUNET_OK, GNUNET_SYSERR, msg, and GNUNET_MessageHeader::size.

◆ handle_monitor_get()

static void handle_monitor_get ( void *  cls,
const struct GNUNET_DHT_MonitorGetMessage msg 
)
static

Process a get monitor message from the service.

Parameters
clsThe DHT handle.
msgMonitor get message from the service.

Definition at line 515 of file dht_api.c.

517 {
518  struct GNUNET_DHT_Handle *handle = cls;
520 
521  for (mh = handle->monitor_head; NULL != mh; mh = mh->next)
522  {
523  if (NULL == mh->get_cb)
524  continue;
525  if (((GNUNET_BLOCK_TYPE_ANY == mh->type) ||
526  (mh->type == ntohl (msg->type))) &&
527  ((NULL == mh->key) ||
528  (0 == memcmp (mh->key,
529  &msg->key,
530  sizeof(struct GNUNET_HashCode)))))
531  mh->get_cb (mh->cb_cls,
532  ntohl (msg->options),
533  (enum GNUNET_BLOCK_Type) ntohl (msg->type),
534  ntohl (msg->hop_count),
535  ntohl (msg->desired_replication_level),
536  ntohl (msg->get_path_length),
537  (struct GNUNET_PeerIdentity *) &msg[1],
538  &msg->key);
539  }
540 }
GNUNET_BLOCK_Type
Blocks in the datastore and the datacache must have a unique type.
@ GNUNET_BLOCK_TYPE_ANY
Any type of block, used as a wildcard when searching.
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.

References GNUNET_BLOCK_TYPE_ANY, handle, mh, msg, and GNUNET_MessageHeader::type.

◆ check_monitor_get_resp()

static int check_monitor_get_resp ( void *  cls,
const struct GNUNET_DHT_MonitorGetRespMessage msg 
)
static

Validate a get response monitor message from the service.

Parameters
clsThe DHT handle.
msgmonitor get response message from the service
Returns
GNUNET_OK if everything went fine, GNUNET_SYSERR if the message is malformed.

Definition at line 552 of file dht_api.c.

554 {
555  size_t msize = ntohs (msg->header.size) - sizeof(*msg);
556  uint32_t getl = ntohl (msg->get_path_length);
557  uint32_t putl = ntohl (msg->put_path_length);
558 
559  if ((getl + putl < getl) ||
560  ((msize / sizeof(struct GNUNET_PeerIdentity)) < getl + putl))
561  {
562  GNUNET_break (0);
563  return GNUNET_SYSERR;
564  }
565  return GNUNET_OK;
566 }

References GNUNET_break, GNUNET_OK, GNUNET_SYSERR, msg, and GNUNET_MessageHeader::size.

◆ handle_monitor_get_resp()

static void handle_monitor_get_resp ( void *  cls,
const struct GNUNET_DHT_MonitorGetRespMessage msg 
)
static

Process a get response monitor message from the service.

Parameters
clsThe DHT handle.
msgmonitor get response message from the service

Definition at line 576 of file dht_api.c.

578 {
579  struct GNUNET_DHT_Handle *handle = cls;
580  size_t msize = ntohs (msg->header.size) - sizeof(*msg);
581  const struct GNUNET_PeerIdentity *path;
582  uint32_t getl = ntohl (msg->get_path_length);
583  uint32_t putl = ntohl (msg->put_path_length);
585 
586  path = (const struct GNUNET_PeerIdentity *) &msg[1];
587  for (mh = handle->monitor_head; NULL != mh; mh = mh->next)
588  {
589  if (NULL == mh->get_resp_cb)
590  continue;
591  if (((GNUNET_BLOCK_TYPE_ANY == mh->type) ||
592  (mh->type == ntohl (msg->type))) &&
593  ((NULL == mh->key) ||
594  (0 == memcmp (mh->key,
595  &msg->key,
596  sizeof(struct GNUNET_HashCode)))))
597  mh->get_resp_cb (mh->cb_cls,
598  (enum GNUNET_BLOCK_Type) ntohl (msg->type),
599  path,
600  getl,
601  &path[getl],
602  putl,
603  GNUNET_TIME_absolute_ntoh (msg->expiration_time),
604  &msg->key,
605  (const void *) &path[getl + putl],
606  msize - sizeof(struct GNUNET_PeerIdentity) * (putl
607  + getl));
608  }
609 }
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_ntoh(struct GNUNET_TIME_AbsoluteNBO a)
Convert absolute time from network byte order.
Definition: time.c:542

References GNUNET_BLOCK_TYPE_ANY, GNUNET_TIME_absolute_ntoh(), handle, mh, msg, GNUNET_MessageHeader::size, and GNUNET_MessageHeader::type.

Here is the call graph for this function:

◆ check_monitor_put()

static int check_monitor_put ( void *  cls,
const struct GNUNET_DHT_MonitorPutMessage msg 
)
static

Check validity of a put monitor message from the service.

Parameters
clsThe DHT handle.
msgMonitor put message from the service.
Returns
GNUNET_OK if everything went fine, GNUNET_SYSERR if the message is malformed.

Definition at line 621 of file dht_api.c.

623 {
624  size_t msize;
625  uint32_t putl;
626 
627  msize = ntohs (msg->header.size) - sizeof(*msg);
628  putl = ntohl (msg->put_path_length);
629  if ((msize / sizeof(struct GNUNET_PeerIdentity)) < putl)
630  {
631  GNUNET_break (0);
632  return GNUNET_SYSERR;
633  }
634  return GNUNET_OK;
635 }

References GNUNET_break, GNUNET_OK, GNUNET_SYSERR, msg, and GNUNET_MessageHeader::size.

◆ handle_monitor_put()

static void handle_monitor_put ( void *  cls,
const struct GNUNET_DHT_MonitorPutMessage msg 
)
static

Process a put monitor message from the service.

Parameters
clsThe DHT handle.
msgMonitor put message from the service.

Definition at line 645 of file dht_api.c.

647 {
648  struct GNUNET_DHT_Handle *handle = cls;
649  size_t msize = ntohs (msg->header.size) - sizeof(*msg);
650  uint32_t putl = ntohl (msg->put_path_length);
651  const struct GNUNET_PeerIdentity *path;
653 
654  path = (const struct GNUNET_PeerIdentity *) &msg[1];
655  for (mh = handle->monitor_head; NULL != mh; mh = mh->next)
656  {
657  if (NULL == mh->put_cb)
658  continue;
659  if (((GNUNET_BLOCK_TYPE_ANY == mh->type) ||
660  (mh->type == ntohl (msg->type))) &&
661  ((NULL == mh->key) ||
662  (0 == memcmp (mh->key,
663  &msg->key,
664  sizeof(struct GNUNET_HashCode)))))
665  mh->put_cb (mh->cb_cls,
666  ntohl (msg->options),
667  (enum GNUNET_BLOCK_Type) ntohl (msg->type),
668  ntohl (msg->hop_count),
669  ntohl (msg->desired_replication_level),
670  putl,
671  path,
672  GNUNET_TIME_absolute_ntoh (msg->expiration_time),
673  &msg->key,
674  (const void *) &path[putl],
675  msize - sizeof(struct GNUNET_PeerIdentity) * putl);
676  }
677 }

References GNUNET_BLOCK_TYPE_ANY, GNUNET_TIME_absolute_ntoh(), handle, mh, msg, GNUNET_MessageHeader::size, and GNUNET_MessageHeader::type.

Here is the call graph for this function:

◆ check_client_result()

static int check_client_result ( void *  cls,
const struct GNUNET_DHT_ClientResultMessage msg 
)
static

Verify that client result message received from the service is well-formed.

Parameters
clsThe DHT handle.
msgMonitor put message from the service.
Returns
GNUNET_OK if everything went fine, GNUNET_SYSERR if the message is malformed.

Definition at line 689 of file dht_api.c.

691 {
692  size_t msize = ntohs (msg->header.size) - sizeof(*msg);
693  uint32_t put_path_length = ntohl (msg->put_path_length);
694  uint32_t get_path_length = ntohl (msg->get_path_length);
695  size_t meta_length;
696 
697  meta_length =
698  sizeof(struct GNUNET_PeerIdentity) * (get_path_length + put_path_length);
699  if ((msize < meta_length) ||
700  (get_path_length >
701  GNUNET_MAX_MESSAGE_SIZE / sizeof(struct GNUNET_PeerIdentity)) ||
702  (put_path_length >
704  {
705  GNUNET_break (0);
706  return GNUNET_SYSERR;
707  }
708  return GNUNET_OK;
709 }

References GNUNET_break, GNUNET_MAX_MESSAGE_SIZE, GNUNET_OK, GNUNET_SYSERR, msg, and GNUNET_MessageHeader::size.

◆ process_client_result()

static int process_client_result ( void *  cls,
const struct GNUNET_HashCode key,
void *  value 
)
static

Process a given reply that might match the given request.

Parameters
clsthe struct GNUNET_DHT_ClientResultMessage
keyquery of the request
valuethe struct GNUNET_DHT_GetHandle of a request matching the same key
Returns
GNUNET_YES to continue to iterate over all results

Definition at line 721 of file dht_api.c.

724 {
725  const struct GNUNET_DHT_ClientResultMessage *crm = cls;
727  size_t msize = ntohs (crm->header.size) - sizeof(*crm);
728  uint32_t put_path_length = ntohl (crm->put_path_length);
729  uint32_t get_path_length = ntohl (crm->get_path_length);
730  const struct GNUNET_PeerIdentity *put_path;
731  const struct GNUNET_PeerIdentity *get_path;
732  struct GNUNET_HashCode hc;
733  size_t data_length;
734  size_t meta_length;
735  const void *data;
736 
737  if (crm->unique_id != get_handle->unique_id)
738  {
739  /* UID mismatch */
741  "Ignoring reply for %s: UID mismatch: %llu/%llu\n",
742  GNUNET_h2s (key),
743  (unsigned long long) crm->unique_id,
744  (unsigned long long) get_handle->unique_id);
745  return GNUNET_YES;
746  }
747  /* FIXME: might want to check that type matches */
748  meta_length =
749  sizeof(struct GNUNET_PeerIdentity) * (get_path_length + put_path_length);
750  data_length = msize - meta_length;
751  put_path = (const struct GNUNET_PeerIdentity *) &crm[1];
752  get_path = &put_path[put_path_length];
753  {
754  char *pp;
755  char *gp;
756 
757  gp = GNUNET_STRINGS_pp2s (get_path,
758  get_path_length);
759  pp = GNUNET_STRINGS_pp2s (put_path,
760  put_path_length);
762  "Giving %u byte reply for %s to application (GP: %s, PP: %s)\n",
763  (unsigned int) data_length,
764  GNUNET_h2s (key),
765  gp,
766  pp);
767  GNUNET_free (gp);
768  GNUNET_free (pp);
769  }
770  data = &get_path[get_path_length];
771  /* remember that we've seen this result */
773  data_length,
774  &hc);
778  get_handle->seen_results_size * 2 + 1);
780  /* no need to block it explicitly, service already knows about it! */
783  key,
784  get_path,
785  get_path_length,
786  put_path,
787  put_path_length,
788  ntohl (crm->type),
789  data_length,
790  data);
791  return GNUNET_YES;
792 }
static struct GNUNET_DHT_GetHandle * get_handle
Handle for the get request.
uint32_t data
The data value.
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:41
#define GNUNET_array_grow(arr, size, tsize)
Grow a well-typed (!) array.
#define GNUNET_free(ptr)
Wrapper around free.
char * GNUNET_STRINGS_pp2s(const struct GNUNET_PeerIdentity *pids, unsigned int num_pids)
Convert a peer path to a human-readable string.
Definition: strings.c:73
uint32_t put_path_length
Number of peers recorded in the outgoing path from source to the storgage location of this message.
Definition: dht.h:159
uint64_t unique_id
Unique ID of the matching GET request.
Definition: dht.h:170
struct GNUNET_TIME_AbsoluteNBO expiration
When does this entry expire?
Definition: dht.h:175
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_DHT_CLIENT_RESULT.
Definition: dht.h:148
uint32_t type
The type for the data.
Definition: dht.h:153
uint32_t get_path_length
The number of peer identities recorded from the storage location to this peer.
Definition: dht.h:165
GNUNET_DHT_GetIterator iter
Iterator to call on data receipt.
Definition: dht_api.c:84
void * iter_cls
Closure for iter.
Definition: dht_api.c:89
unsigned int seen_results_end
Offset into the seen_results array marking the end of the positions that are actually used.
Definition: dht_api.c:142
struct GNUNET_HashCode * seen_results
Array of hash codes over the results that we have already seen.
Definition: dht_api.c:100
uint64_t unique_id
Unique identifier for this request (for key collisions).
Definition: dht_api.c:110
unsigned int seen_results_size
Size of the seen_results array.
Definition: dht_api.c:136

References data, GNUNET_DHT_ClientResultMessage::expiration, get_handle, GNUNET_DHT_ClientResultMessage::get_path_length, GNUNET_array_grow, GNUNET_CRYPTO_hash(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_h2s(), GNUNET_STRINGS_pp2s(), GNUNET_TIME_absolute_ntoh(), GNUNET_YES, GNUNET_DHT_ClientResultMessage::header, GNUNET_DHT_GetHandle::iter, GNUNET_DHT_GetHandle::iter_cls, key, LOG, GNUNET_DHT_ClientResultMessage::put_path_length, GNUNET_DHT_GetHandle::seen_results, GNUNET_DHT_GetHandle::seen_results_end, GNUNET_DHT_GetHandle::seen_results_size, GNUNET_MessageHeader::size, GNUNET_DHT_ClientResultMessage::type, GNUNET_DHT_ClientResultMessage::unique_id, GNUNET_DHT_GetHandle::unique_id, and value.

Referenced by handle_client_result().

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

◆ handle_client_result()

static void handle_client_result ( void *  cls,
const struct GNUNET_DHT_ClientResultMessage msg 
)
static

Process a client result message received from the service.

Parameters
clsThe DHT handle.
msgMonitor put message from the service.

Definition at line 802 of file dht_api.c.

804 {
805  struct GNUNET_DHT_Handle *handle = cls;
806 
808  &msg->key,
810  (void *) msg);
811 }
static int process_client_result(void *cls, const struct GNUNET_HashCode *key, void *value)
Process a given reply that might match the given request.
Definition: dht_api.c:721
int GNUNET_CONTAINER_multihashmap_get_multiple(struct GNUNET_CONTAINER_MultiHashMap *map, const struct GNUNET_HashCode *key, GNUNET_CONTAINER_MulitHashMapIteratorCallback it, void *it_cls)
Iterate over all entries in the map that match a particular key.

References GNUNET_CONTAINER_multihashmap_get_multiple(), handle, msg, and process_client_result().

Here is the call graph for this function:

◆ handle_put_cont()

static void handle_put_cont ( void *  cls)
static

Process a MQ PUT transmission notification.

Parameters
clsThe DHT handle.

Definition at line 820 of file dht_api.c.

821 {
822  struct GNUNET_DHT_PutHandle *ph = cls;
824  void *cont_cls;
825 
826  cont = ph->cont;
827  cont_cls = ph->cont_cls;
828  ph->env = NULL;
830  if (NULL != cont)
831  cont (cont_cls);
832 }

References GNUNET_DHT_PutHandle::cont, GNUNET_DHT_PutHandle::cont_cls, GNUNET_DHT_put_cancel(), and ph.

Referenced by GNUNET_DHT_put().

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