GNUnet  0.10.x
gnunet-service-rps_sampler.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet.
3  Copyright (C)
4 
5  GNUnet is free software: you can redistribute it and/or modify it
6  under the terms of the GNU Affero General Public License as published
7  by the Free Software Foundation, either version 3 of the License,
8  or (at your option) any later version.
9 
10  GNUnet is distributed in the hope that it will be useful, but
11  WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  Affero General Public License for more details.
14 
15  You should have received a copy of the GNU Affero General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17 
18  SPDX-License-Identifier: AGPL3.0-or-later
19 */
20 
26 #include "platform.h"
27 #include "gnunet_util_lib.h"
29 #include "rps.h"
30 
31 #include "rps-sampler_common.h"
34 
35 #include <math.h>
36 #include <inttypes.h>
37 
38 #include "rps-test_util.h"
39 
40 #define LOG(kind, ...) GNUNET_log_from(kind,"rps-sampler",__VA_ARGS__)
41 
42 
43 // multiple 'clients'?
44 
45 // TODO check for overflows
46 
47 // TODO align message structs
48 
49 // hist_size_init, hist_size_max
50 
51 /***********************************************************************
52  * WARNING: This section needs to be reviewed regarding the use of
53  * functions providing (pseudo)randomness!
54 ***********************************************************************/
55 
56 // TODO care about invalid input of the caller (size 0 or less...)
57 
63 typedef void
64 (*SamplerNotifyUpdateCB) (void *cls);
65 
72 {
77 
81  void *cls;
82 
87 
92 };
93 
94 
99 typedef void
101 
109 static void
110 sampler_get_rand_peer (void *cls);
111 
112 
117 {
123 
127  uint32_t num_peers;
128 
132  uint32_t cur_num_peers;
133 
138 
144 
149 
154 
158  void *cls;
159 };
160 
162 // * Global sampler variable.
163 // */
164 //struct RPS_Sampler *sampler;
165 
166 
170 static size_t min_size;
171 
175 static size_t max_size;
176 
180 //static size_t extra_size;
181 
185 static uint32_t client_get_index;
186 
187 
195 struct RPS_Sampler *
196 RPS_sampler_init (size_t init_size,
198 {
199  struct RPS_Sampler *sampler;
200 
201  /* Initialise context around extended sampler */
202  min_size = 10; // TODO make input to _samplers_init()
203  max_size = 1000; // TODO make input to _samplers_init()
204 
205  sampler = GNUNET_new (struct RPS_Sampler);
206 
208  sampler->get_peers = sampler_get_rand_peer;
209  //sampler->sampler_elements = GNUNET_new_array(init_size, struct GNUNET_PeerIdentity);
210  //GNUNET_array_grow (sampler->sampler_elements, sampler->sampler_size, min_size);
211  RPS_sampler_resize (sampler, init_size);
212 
213  client_get_index = 0;
214 
215  //GNUNET_assert (init_size == sampler->sampler_size);
216  return sampler;
217 }
218 
226 static void
228 {
229  struct GetPeerCls *gpc = cls;
230  uint32_t r_index;
231  struct RPS_Sampler *sampler;
232 
233  gpc->get_peer_task = NULL;
234  gpc->notify_ctx = NULL;
235  sampler = gpc->req_handle->sampler;
236 
242  sampler->sampler_size);
243 
244  if (EMPTY == sampler->sampler_elements[r_index]->is_empty)
245  {
246  //LOG (GNUNET_ERROR_TYPE_DEBUG,
247  // "Not returning randomly selected, empty PeerID. - Rescheduling.\n");
248 
249  gpc->notify_ctx =
250  sampler_notify_on_update (sampler,
252  gpc);
253  return;
254  }
255 
257  gpc->req_handle->gpc_tail,
258  gpc);
259  *gpc->id = sampler->sampler_elements[r_index]->peer_id;
260  gpc->cont (gpc->cont_cls, gpc->id, 0, sampler->sampler_elements[r_index]->num_peers);
261 
262  GNUNET_free (gpc);
263 }
264 
265 
266 /* end of gnunet-service-rps.c */
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
uint32_t num_peers
How many times a PeerID was put in this sampler.
RPS_sampler_rand_peer_ready_cont cont
The callback.
struct SamplerNotifyUpdateCTX * prev
Previous element in DLL.
static void sampler_get_rand_peer(void *cls)
Get one random peer out of the sampled peers.
uint32_t num_peers
Number of peers we are waiting for.
uint64_t GNUNET_CRYPTO_random_u64(enum GNUNET_CRYPTO_Quality mode, uint64_t max)
Random on unsigned 64-bit values.
Some utils faciliating the view into the internals for the sampler needed for evaluation.
void * cls
Closure given to the callback.
static size_t min_size
Global sampler variable.
sampler element implementation
RPS_sampler_n_rand_peers_ready_cb callback
Callback to be called when all ids are available.
Code common to client and service sampler.
Context for a callback.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
example IPC messages between RPS API and GNS service
struct RPS_SamplerRequestHandle * next
DLL.
struct RPS_SamplerRequestHandle * req_handle
The RPS_SamplerRequestHandle this single request belongs to.
struct GNUNET_TIME_Relative max_round_interval
Maximum time a round takes.
void(* SamplerNotifyUpdateCB)(void *cls)
Callback called each time a new peer was put into the sampler.
void(* RPS_get_peers_type)(void *cls)
Type of function used to differentiate between modified and not modified Sampler. ...
Closure to _get_n_rand_peers_ready_cb()
struct SamplerNotifyUpdateCTX * notify_ctx
Context to the given callback.
struct RPS_Sampler * RPS_sampler_init(size_t init_size, struct GNUNET_TIME_Relative max_round_interval)
Initialise a tuple of sampler elements.
struct SamplerNotifyUpdateCTX * next
Next element in DLL.
enum RPS_SamplerEmpty is_empty
Flag that indicates that we are not holding a valid PeerID right now.
static uint32_t client_get_index
The size the extended sampler elements currently have.
struct GNUNET_PeerIdentity peer_id
The PeerID this sampler currently samples.
SamplerNotifyUpdateCB notify_cb
The Callback to call on updates.
void * cls
The according closure.
void RPS_sampler_resize(struct RPS_Sampler *sampler, unsigned int new_size)
Grow or shrink the size of the sampler.
struct GetPeerCls * gpc_head
Head and tail for the DLL to store the tasks for single requests.
static size_t max_size
The maximal size the extended sampler elements should grow to.
struct GNUNET_PeerIdentity * ids
Pointer to the array holding the ids.
sampler implementation
uint32_t cur_num_peers
Number of peers we currently have.
void * cont_cls
The closure to the callback cont.
The identity of the host (wraps the signing key of the peer).
void(* RPS_sampler_n_rand_peers_ready_cb)(const struct GNUNET_PeerIdentity *ids, uint32_t num_peers, void *cls)
Callback that is called from _get_n_rand_peers() when the PeerIDs are ready.
struct SamplerNotifyUpdateCTX * sampler_notify_on_update(struct RPS_Sampler *sampler, SamplerNotifyUpdateCB notify_cb, void *cls)
Add a callback that will be called when the next peer is inserted into the sampler.
Closure for sampler_mod_get_rand_peer() and sampler_get_rand_peer.
unsigned int sampler_size
Number of sampler elements we hold.
RPS_get_peers_type get_peers
Stores the function to return peers.
struct RPS_SamplerElement ** sampler_elements
All sampler elements in one array.
struct RPS_SamplerRequestHandle * prev
Sampler with its own array of SamplerElements.
struct GNUNET_PeerIdentity * id
The address of the id to be stored at.
struct GNUNET_SCHEDULER_Task * get_peer_task
The task for this function.
#define GNUNET_free(ptr)
Wrapper around free.
Time for relative time used by GNUnet, in microseconds.
struct RPS_Sampler * sampler
Sampler.
High-quality operations are desired.