GNUnet  0.10.x
gnunet-nse-profiler.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet.
3  Copyright (C) 2011, 2012 GNUnet e.V.
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  */
32 #include "platform.h"
33 #include "gnunet_testbed_service.h"
34 #include "gnunet_nse_service.h"
35 
39 #define LOG(kind, ...) GNUNET_log(kind, __VA_ARGS__)
40 
44 #define LOG_DEBUG(...) LOG(GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__)
45 
46 
50 struct NSEPeer {
54  struct NSEPeer *prev;
55 
59  struct NSEPeer *next;
60 
65 
70 
75 
80 };
81 
82 
86 struct OpListEntry {
90  struct OpListEntry *next;
91 
95  struct OpListEntry *prev;
96 
101 
106  int delta;
107 };
108 
109 
113 static struct NSEPeer *peer_head;
114 
118 static struct NSEPeer *peer_tail;
119 
123 static int ok;
124 
128 static unsigned int verbose;
129 
133 static char *hosts_file;
134 
138 static unsigned int num_peers;
139 
143 static unsigned int num_rounds;
144 
148 static unsigned int current_round;
149 
153 static unsigned int *num_peers_in_round;
154 
158 static unsigned int peers_running;
159 
163 static char *num_peer_spec;
164 
168 static struct GNUNET_TESTBED_Peer **daemons;
169 
174 
178 static unsigned int connection_limit;
179 
183 static unsigned int total_connections;
184 
189 
193 static char *output_filename;
194 
199 
203 static char *data_filename;
204 
209 static struct GNUNET_TIME_Relative wait_time = { 60 * 1000 };
210 
214 static struct OpListEntry *oplist_head;
215 
219 static struct OpListEntry *oplist_tail;
220 
225 
226 
231 static void
233 {
234  struct NSEPeer *pos;
235  struct OpListEntry *oplist_entry;
236 
237  while (NULL != (pos = peer_head))
238  {
239  if (NULL != pos->nse_op)
241  if (NULL != pos->stat_op)
243  GNUNET_CONTAINER_DLL_remove(peer_head, peer_tail, pos);
244  GNUNET_free(pos);
245  }
246  while (NULL != (oplist_entry = oplist_head))
247  {
248  GNUNET_CONTAINER_DLL_remove(oplist_head, oplist_tail, oplist_entry);
249  GNUNET_TESTBED_operation_done(oplist_entry->op);
250  GNUNET_free(oplist_entry);
251  }
252 }
253 
254 
260 static void
261 shutdown_task(void *cls)
262 {
263  LOG_DEBUG("Ending test.\n");
265  if (NULL != round_task)
266  {
267  GNUNET_SCHEDULER_cancel(round_task);
268  round_task = NULL;
269  }
270  if (NULL != data_file)
271  {
272  GNUNET_DISK_file_close(data_file);
273  data_file = NULL;
274  }
275  if (NULL != output_file)
276  {
277  GNUNET_DISK_file_close(output_file);
278  output_file = NULL;
279  }
280  if (NULL != testing_cfg)
281  {
282  GNUNET_CONFIGURATION_destroy(testing_cfg);
283  testing_cfg = NULL;
284  }
285 }
286 
287 
297 static void
298 handle_estimate(void *cls,
299  struct GNUNET_TIME_Absolute timestamp,
300  double estimate,
301  double std_dev)
302 {
303  struct NSEPeer *peer = cls;
304  char output_buffer[512];
305  size_t size;
306 
307  if (NULL == output_file)
308  {
309  fprintf(stderr,
310  "Received network size estimate from peer %p. Size: %f std.dev. %f\n",
311  peer,
312  estimate,
313  std_dev);
314  return;
315  }
316  size = GNUNET_snprintf(output_buffer,
317  sizeof(output_buffer),
318  "%p %llu %llu %f %f %f\n",
319  peer,
321  (unsigned long long)timestamp.abs_value_us,
323  estimate,
324  std_dev);
325  if (size != GNUNET_DISK_file_write(output_file, output_buffer, size))
326  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n");
327 }
328 
329 
340 static void *
342 {
343  struct NSEPeer *current_peer = cls;
344 
345  return GNUNET_NSE_connect(cfg, &handle_estimate, current_peer);
346 }
347 
348 
356 static void
358 {
359  GNUNET_NSE_disconnect(op_result);
360 }
361 
362 
373 static int
374 stat_iterator(void *cls,
375  const char *subsystem,
376  const char *name,
377  uint64_t value,
378  int is_persistent)
379 {
380  char *output_buffer;
381  struct GNUNET_TIME_Absolute now;
382  int size;
383  unsigned int flag;
384 
385  GNUNET_assert(NULL != data_file);
386  now = GNUNET_TIME_absolute_get();
387  flag = strcasecmp(subsystem, "core");
388  if (0 != flag)
389  flag = 1;
390  size = GNUNET_asprintf(&output_buffer,
391  "%llu %llu %u\n",
392  now.abs_value_us / 1000LL / 1000LL,
393  value,
394  flag);
395  if (0 > size)
396  {
397  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Error formatting output buffer.\n");
398  GNUNET_free(output_buffer);
399  return GNUNET_SYSERR;
400  }
401  if (size != GNUNET_DISK_file_write(data_file, output_buffer, (size_t)size))
402  {
403  GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n");
404  GNUNET_free(output_buffer);
405  return GNUNET_SYSERR;
406  }
407  GNUNET_free(output_buffer);
408  return GNUNET_OK;
409 }
410 
411 
421 static void *
423 {
424  struct NSEPeer *peer = cls;
425 
426  peer->sh = GNUNET_STATISTICS_create("nse-profiler", cfg);
427  return peer->sh;
428 }
429 
430 
437 static void
439 {
440  struct NSEPeer *peer = cls;
441 
444  "core",
445  "# peers connected",
447  peer));
450  "nse",
451  "# peers connected",
453  peer));
455  peer->sh = NULL;
456 }
457 
458 
469 static void
470 stat_comp_cb(void *cls,
472  void *ca_result,
473  const char *emsg)
474 {
475  struct GNUNET_STATISTICS_Handle *sh = ca_result;
476  struct NSEPeer *peer = cls;
477 
478  if (NULL != emsg)
479  {
480  GNUNET_break(0);
481  return;
482  }
484  "core",
485  "# peers connected",
487  peer));
489  "nse",
490  "# peers connected",
492  peer));
493 }
494 
495 
500 static void
502 {
503  struct NSEPeer *current_peer;
504  unsigned int i;
505  unsigned int connections;
506 
507  if (0 == connection_limit)
508  return;
509  LOG_DEBUG("Connecting to nse service of peers\n");
510  connections = 0;
511  for (i = 0; i < num_peers_in_round[current_round]; i++)
512  {
513  if ((num_peers_in_round[current_round] > connection_limit) &&
514  (0 != (i % (num_peers_in_round[current_round] / connection_limit))))
515  continue;
516  LOG_DEBUG("Connecting to nse service of peer %d\n", i);
517  current_peer = GNUNET_new(struct NSEPeer);
518  current_peer->daemon = daemons[i];
519  current_peer->nse_op =
521  current_peer->daemon,
522  "nse",
523  NULL,
524  NULL,
527  current_peer);
528  if (NULL != data_file)
529  current_peer->stat_op =
531  current_peer->daemon,
532  "statistics",
533  stat_comp_cb,
534  current_peer,
537  current_peer);
538  GNUNET_CONTAINER_DLL_insert(peer_head, peer_tail, current_peer);
539  if (++connections == connection_limit)
540  break;
541  }
542 }
543 
544 
550 static void
551 next_round(void *cls);
552 
553 
561 static void
562 finish_round(void *cls)
563 {
564  LOG(GNUNET_ERROR_TYPE_INFO, "Have %u connections\n", total_connections);
566  round_task = GNUNET_SCHEDULER_add_now(&next_round, NULL);
567 }
568 
569 
575 static void
577 {
578  LOG_DEBUG("Running round %u\n", current_round);
580  GNUNET_SCHEDULER_add_delayed(wait_time, &finish_round, NULL);
581 }
582 
583 
587 static struct OpListEntry *
589 {
590  struct OpListEntry *entry;
591 
592  entry = GNUNET_new(struct OpListEntry);
593  GNUNET_CONTAINER_DLL_insert_tail(oplist_head, oplist_tail, entry);
594  return entry;
595 }
596 
597 
605 static void
608  const char *emsg)
609 {
610  struct OpListEntry *entry = cls;
611 
613  if (NULL != emsg)
614  {
615  LOG(GNUNET_ERROR_TYPE_ERROR, "Failed to start/stop NSE at a peer\n");
617  return;
618  }
619  GNUNET_assert(0 != entry->delta);
620  peers_running += entry->delta;
621  GNUNET_CONTAINER_DLL_remove(oplist_head, oplist_tail, entry);
622  GNUNET_free(entry);
624  run_round();
625 }
626 
627 
632 static void
634 {
635  struct OpListEntry *entry;
636  unsigned int i;
637 
638  /* start peers if we have too few */
639  for (i = peers_running; i < num_peers_in_round[current_round]; i++)
640  {
641  entry = make_oplist_entry();
642  entry->delta = 1;
644  daemons[i],
645  "nse",
647  entry,
648  1);
649  }
650  /* stop peers if we have too many */
651  for (i = num_peers_in_round[current_round]; i < peers_running; i++)
652  {
653  entry = make_oplist_entry();
654  entry->delta = -1;
656  daemons[i],
657  "nse",
659  entry,
660  0);
661  }
662 }
663 
664 
671 static void
672 next_round(void *cls)
673 {
674  round_task = NULL;
675  LOG_DEBUG("Disconnecting nse service of peers\n");
676  current_round++;
677  if (current_round == num_rounds)
678  {
679  /* this was the last round, terminate */
680  ok = 0;
682  return;
683  }
685  {
686  /* no need to churn, just run next round */
687  run_round();
688  return;
689  }
691 }
692 
693 
701 static void
703  const struct GNUNET_TESTBED_EventInformation *event)
704 {
705  switch (event->type)
706  {
709  break;
710 
713  break;
714 
715  default:
716  break;
717  }
718 }
719 
720 
734 static void
735 test_master(void *cls,
736  struct GNUNET_TESTBED_RunHandle *h,
737  unsigned int num_peers_,
738  struct GNUNET_TESTBED_Peer **peers,
739  unsigned int links_succeeded,
740  unsigned int links_failed)
741 {
742  if (NULL == peers)
743  {
745  return;
746  }
747  daemons = peers;
748  GNUNET_break(num_peers_ == num_peers);
751  {
752  /* no need to churn, just run the starting round */
753  run_round();
754  return;
755  }
757 }
758 
759 
768 static void
769 run(void *cls,
770  char *const *args,
771  const char *cfgfile,
772  const struct GNUNET_CONFIGURATION_Handle *cfg)
773 {
774  char *tok;
775  uint64_t event_mask;
776  unsigned int num;
777 
778  ok = 1;
779  testing_cfg = GNUNET_CONFIGURATION_dup(cfg);
780  LOG_DEBUG("Starting daemons.\n");
781  if (NULL == num_peer_spec)
782  {
783  fprintf(stderr, "You need to specify the number of peers to run\n");
784  return;
785  }
786  for (tok = strtok(num_peer_spec, ","); NULL != tok; tok = strtok(NULL, ","))
787  {
788  if (1 != sscanf(tok, "%u", &num))
789  {
790  fprintf(stderr, "You need to specify numbers, not `%s'\n", tok);
791  return;
792  }
793  if (0 == num)
794  {
795  fprintf(stderr, "Refusing to run a round with 0 peers\n");
796  return;
797  }
800  }
801  if (0 == num_peers)
802  {
803  fprintf(stderr, "Refusing to run a testbed with no rounds\n");
804  return;
805  }
806  if ((NULL != data_filename) &&
807  (NULL ==
815 
816  if ((NULL != output_filename) &&
817  (NULL ==
818  (output_file = GNUNET_DISK_file_open(output_filename,
824  event_mask = 0LL;
825  event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_START);
826  event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_STOP);
827  event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT);
828  event_mask |= (1LL << GNUNET_TESTBED_ET_DISCONNECT);
830  cfg,
831  num_peers,
832  event_mask,
834  NULL, /* master_controller_cb cls */
835  &test_master,
836  NULL); /* test_master cls */
838 }
839 
840 
846 int
847 main(int argc, char *const *argv)
848 {
849  struct GNUNET_GETOPT_CommandLineOption options[] =
851  'C',
852  "connections",
853  "COUNT",
854  gettext_noop(
855  "limit to the number of connections to NSE services, 0 for none"),
858  'd',
859  "details",
860  "FILENAME",
861  gettext_noop(
862  "name of the file for writing connection information and statistics"),
863  &data_filename),
864 
866  'H',
867  "hosts",
868  "FILENAME",
869  gettext_noop(
870  "name of the file with the login information for the testbed"),
871  &hosts_file),
872 
874  'o',
875  "output",
876  "FILENAME",
877  gettext_noop("name of the file for writing the main results"),
878  &output_filename),
879 
880 
882  'p',
883  "peers",
884  "NETWORKSIZESPEC",
885  gettext_noop(
886  "Number of peers to run in each round, separated by commas"),
887  &num_peer_spec),
888 
890  'V',
891  "verbose",
892  gettext_noop("be verbose (print progress information)"),
893  &verbose),
894 
896  "wait",
897  "DELAY",
898  gettext_noop("delay between rounds"),
899  &wait_time),
901 
902  if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args(argc, argv, &argc, &argv))
903  return 2;
904  if (
905  GNUNET_OK !=
906  GNUNET_PROGRAM_run(argc,
907  argv,
908  "nse-profiler",
909  gettext_noop(
910  "Measure quality and performance of the NSE service."),
911  options,
912  &run,
913  NULL))
914  ok = 1;
915  return ok;
916 }
917 
918 /* end of nse-profiler.c */
struct GNUNET_GETOPT_CommandLineOption GNUNET_GETOPT_option_relative_time(char shortName, const char *name, const char *argumentHelp, const char *description, struct GNUNET_TIME_Relative *val)
Allow user to specify a struct GNUNET_TIME_Relative (using human-readable "fancy" time)...
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
static void close_monitor_connections()
Clean up all of the monitoring connections to NSE and STATISTICS that we keep to selected peers...
static void next_round(void *cls)
Task that starts/stops peers to move to the next round.
struct OpListEntry * prev
DLL prev ptr.
Create file if it doesn&#39;t exist.
struct NSEPeer * next
Next reference in DLL.
static char * subsystem
Set to subsystem that we&#39;re going to get stats for (or NULL for all).
int GNUNET_DISK_file_close(struct GNUNET_DISK_FileHandle *h)
Close an open file.
Definition: disk.c:1339
static struct GNUNET_TESTBED_Peer ** daemons
Handles to all of the running peers.
#define GNUNET_CONTAINER_DLL_insert(head, tail, element)
Insert an element at the head of a DLL.
int GNUNET_snprintf(char *buf, size_t size, const char *format,...)
Like snprintf, just aborts if the buffer is of insufficient size.
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
struct GNUNET_STATISTICS_Handle * GNUNET_STATISTICS_create(const char *subsystem, const struct GNUNET_CONFIGURATION_Handle *cfg)
Get handle for the statistics service.
int GNUNET_STRINGS_get_utf8_args(int argc, char *const *argv, int *u8argc, char *const **u8argv)
Returns utf-8 encoded arguments.
Definition: strings.c:1439
struct GNUNET_GETOPT_CommandLineOption GNUNET_GETOPT_option_increment_uint(char shortName, const char *name, const char *description, unsigned int *val)
Increment val each time the option flag is given by one.
static unsigned int current_round
Current round we are in.
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
static int op_result(struct GNUNET_OP_Handle *h, uint64_t op_id, int64_t result_code, const void *data, uint16_t data_size, void **ctx, uint8_t cancel)
Remove an operation, and call its result callback (unless it was cancelled).
Definition: op.c:243
struct GNUNET_NSE_Handle * GNUNET_NSE_connect(const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_NSE_Callback func, void *func_cls)
Connect to the network size estimation service.
Definition: nse_api.c:164
static struct NSEPeer * peer_head
Head of DLL of peers we monitor closely.
static void * stat_connect_adapter(void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg)
Called to open a connection to the peer&#39;s statistics.
static int ok
Return value from &#39;main&#39; (0 == success)
Argument to GNUNET_TESTBED_ControllerCallback with details about the event.
static void test_master(void *cls, struct GNUNET_TESTBED_RunHandle *h, unsigned int num_peers_, struct GNUNET_TESTBED_Peer **peers, unsigned int links_succeeded, unsigned int links_failed)
Signature of a main function for a testcase.
#define GNUNET_NO
Definition: gnunet_common.h:78
static struct GNUNET_DISK_FileHandle * data_file
File to log connection info, statistics to.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
enum GNUNET_TESTBED_EventType type
Type of the event.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
Definition of a command line option.
static char * hosts_file
Name of the file with the hosts to run the test over (configuration option)
void GNUNET_STATISTICS_destroy(struct GNUNET_STATISTICS_Handle *h, int sync_first)
Destroy a handle (free all state associated with it).
void GNUNET_SCHEDULER_shutdown(void)
Request the shutdown of a scheduler.
Definition: scheduler.c:517
Handle for the service.
struct GNUNET_CONTAINER_MultiShortmap * connections
Map from struct GNUNET_CADET_ConnectionTunnelIdentifier hash codes to struct CadetConnection objects...
uint64_t abs_value_us
The actual value.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
static void master_controller_cb(void *cls, const struct GNUNET_TESTBED_EventInformation *event)
Function that will be called whenever something in the testbed changes.
static struct OpListEntry * make_oplist_entry()
Creates an oplist entry and adds it to the oplist DLL.
struct GNUNET_GETOPT_CommandLineOption GNUNET_GETOPT_OPTION_END
Definition: 002.c:13
static struct GNUNET_ARM_Handle * h
Connection with ARM.
Definition: gnunet-arm.c:94
Opaque handle to an abstract operation to be executed by the testing framework.
struct GNUNET_GETOPT_CommandLineOption GNUNET_GETOPT_option_string(char shortName, const char *name, const char *argumentHelp, const char *description, char **str)
Allow user to specify a string.
static struct OpListEntry * oplist_head
DLL head for operation list.
struct GNUNET_TESTBED_Operation * nse_op
Testbed operation to connect to NSE service.
static void shutdown_task(void *cls)
Task run on shutdown; cleans up everything.
struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_service_connect(void *op_cls, struct GNUNET_TESTBED_Peer *peer, const char *service_name, GNUNET_TESTBED_ServiceConnectCompletionCallback cb, void *cb_cls, GNUNET_TESTBED_ConnectAdapter ca, GNUNET_TESTBED_DisconnectAdapter da, void *cada_cls)
Connect to a service offered by the given peer.
struct NSEPeer * prev
Prev reference in DLL.
int GNUNET_asprintf(char **buf, const char *format,...)
Like asprintf, just portable.
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:1237
Information we track for a peer in the testbed.
static struct OpListEntry * oplist_tail
DLL tail for operation list.
static void handle_estimate(void *cls, struct GNUNET_TIME_Absolute timestamp, double estimate, double std_dev)
Callback to call when network size estimate is updated.
struct GNUNET_TESTBED_Peer * daemon
Handle with testbed.
static char * value
Value of the record to add/remove.
static struct GNUNET_SCHEDULER_Task * round_task
Task running each round of the experiment.
#define GNUNET_log_strerror_file(level, cmd, filename)
Log an error message at log-level &#39;level&#39; that indicates a failure of the command &#39;cmd&#39; with the mess...
static unsigned int num_peers
Maximum number of peers in the test.
Truncate file if it exists.
ssize_t GNUNET_DISK_file_write(const struct GNUNET_DISK_FileHandle *h, const void *buffer, size_t n)
Write a buffer to a file.
Definition: disk.c:817
#define GNUNET_MAX(a, b)
Definition: gnunet_common.h:82
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_now(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run as soon as possible.
Definition: scheduler.c:1264
static char * data_filename
Filename to log connection info, statistics to.
Operation map entry.
static struct NSEPeer * peer_tail
Tail of DLL of peers we monitor closely.
static unsigned int verbose
Be verbose (configuration option)
void GNUNET_CONFIGURATION_destroy(struct GNUNET_CONFIGURATION_Handle *cfg)
Destroy configuration object.
static unsigned int total_connections
Total number of connections in the whole network.
static struct GNUNET_TIME_Relative wait_time
How long to wait before triggering next round? Default: 60 s.
void GNUNET_TESTBED_operation_done(struct GNUNET_TESTBED_Operation *operation)
This function is used to signal that the event information (struct GNUNET_TESTBED_EventInformation) f...
Definition: testbed_api.c:2037
static struct GNUNET_CONFIGURATION_Handle * testing_cfg
Global configuration file.
void GNUNET_TESTBED_run(const char *host_filename, const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned int num_peers, uint64_t event_mask, GNUNET_TESTBED_ControllerCallback cc, void *cc_cls, GNUNET_TESTBED_TestMaster test_master, void *test_master_cls)
Convenience method for running a testbed with a single call.
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_get(void)
Get the current time.
Definition: time.c:118
A connection between two peers was torn down.
static unsigned int connection_limit
Maximum number of connections to NSE services.
void GNUNET_NSE_disconnect(struct GNUNET_NSE_Handle *h)
Disconnect from network size estimation service.
Definition: nse_api.c:192
static void finish_round(void *cls)
We&#39;re at the end of a round.
static struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
Definition: gnunet-arm.c:104
uint64_t event_mask
Global event mask for all testbed events.
struct GNUNET_TESTBED_Peer * peer
The peer associated with this model.
#define GNUNET_SYSERR
Definition: gnunet_common.h:76
static unsigned int size
Size of the "table".
Definition: peer.c:66
const char * name
static void adjust_running_peers()
Adjust the number of running peers to match the required number of running peers for the round...
#define GNUNET_CONTAINER_DLL_insert_tail(head, tail, element)
Insert an element at the tail of a DLL.
static void stat_comp_cb(void *cls, struct GNUNET_TESTBED_Operation *op, void *ca_result, const char *emsg)
Called after successfully opening a connection to a peer&#39;s statistics service; we register statistics...
A connection between two peers was established.
int delta
Depending on whether we start or stop NSE service at the peer set this to 1 or -1.
static unsigned int num_rounds
Total number of rounds to execute.
struct GNUNET_CONFIGURATION_Handle * GNUNET_CONFIGURATION_dup(const struct GNUNET_CONFIGURATION_Handle *cfg)
Duplicate an existing configuration object.
struct GNUNET_STATISTICS_Handle * sh
Handle to the statistics service.
static unsigned int * num_peers_in_round
Array of size &#39;num_rounds&#39; with the requested number of peers in the given round. ...
#define GNUNET_array_append(arr, size, element)
Append an element to a list (growing the list by one).
int GNUNET_STATISTICS_watch_cancel(struct GNUNET_STATISTICS_Handle *handle, const char *subsystem, const char *name, GNUNET_STATISTICS_Iterator proc, void *proc_cls)
Stop watching statistics from the peer.
int main(int argc, char *const *argv)
Main function.
static void run(void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg)
Actual main function that runs the emulation.
#define LOG(kind,...)
Generic loggins shorthand.
configuration data
Definition: configuration.c:83
static void nse_disconnect_adapter(void *cls, void *op_result)
Adapter function called to destroy a connection to NSE service.
static struct CadetPeer * peers
Operation to get peer ids.
static char * num_peer_spec
Specification for the numbers of peers to have in each round.
int GNUNET_STATISTICS_watch(struct GNUNET_STATISTICS_Handle *handle, const char *subsystem, const char *name, GNUNET_STATISTICS_Iterator proc, void *proc_cls)
Watch statistics from the peer (be notified whenever they change).
static void connect_nse_service()
Task run to connect to the NSE and statistics services to a subset of all of the running peers...
#define GNUNET_log(kind,...)
Entry in list of pending tasks.
Definition: scheduler.c:131
static int stat_iterator(void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent)
Callback function to process statistic values.
Open the file for both reading and writing.
static void run_round()
We have reached the desired number of peers for the current round.
int GNUNET_PROGRAM_run(int argc, char *const *argv, const char *binaryName, const char *binaryHelp, const struct GNUNET_GETOPT_CommandLineOption *options, GNUNET_PROGRAM_Main task, void *task_cls)
Run a standard GNUnet command startup sequence (initialize loggers and configuration, parse options).
Definition: program.c:367
static void manage_service_cb(void *cls, struct GNUNET_TESTBED_Operation *op, const char *emsg)
Callback to be called when NSE service is started or stopped at peers.
Time for absolute times used by GNUnet, in microseconds.
static void * nse_connect_adapter(void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg)
Adapter function called to establish a connection to NSE service.
struct GNUNET_GETOPT_CommandLineOption GNUNET_GETOPT_option_uint(char shortName, const char *name, const char *argumentHelp, const char *description, unsigned int *val)
Allow user to specify an unsigned int.
static struct GNUNET_ARM_Operation * op
Current operation.
Definition: gnunet-arm.c:139
A peer controlled by the testing framework.
A peer has been stopped.
static unsigned int peers_running
How many peers are running right now?
struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_manage_service(void *op_cls, struct GNUNET_TESTBED_Peer *peer, const char *service_name, GNUNET_TESTBED_OperationCompletionCallback cb, void *cb_cls, unsigned int start)
Start or stop given service at a peer.
struct GNUNET_DISK_FileHandle * GNUNET_DISK_file_open(const char *fn, enum GNUNET_DISK_OpenFlags flags, enum GNUNET_DISK_AccessPermissions perm)
Open a file.
Definition: disk.c:1262
#define GNUNET_NSE_log_estimate_to_n(loge)
Convert the logarithmic estimated returned to the &#39;GNUNET_NSE_Callback&#39; into an absolute estimate in ...
struct GNUNET_TESTBED_Operation * stat_op
Testbed operation to connect to statistics service.
Handle used to access files (and pipes).
struct OpListEntry * next
DLL next ptr.
struct GNUNET_TESTBED_Operation * op
The testbed operation.
#define LOG_DEBUG(...)
Debug logging shorthand.
static struct GNUNET_DISK_FileHandle * output_file
File to report results to.
static void stat_disconnect_adapter(void *cls, void *op_result)
Called to disconnect from peer&#39;s statistics service.
static char * output_filename
Filename to log results to.
#define GNUNET_free(ptr)
Wrapper around free.
Time for relative time used by GNUnet, in microseconds.
#define gettext_noop(String)
Definition: gettext.h:69
void * GNUNET_SCHEDULER_cancel(struct GNUNET_SCHEDULER_Task *task)
Cancel the task with the specified identifier.
Definition: scheduler.c:956