moved eval tool to ats
[oweals/gnunet.git] / src / ats / gnunet-ats-solver-eval.h
1 /*
2  This file is part of GNUnet.
3  (C) 2010-2013 Christian Grothoff (and other contributing authors)
4
5  GNUnet is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published
7  by the Free Software Foundation; either version 3, or (at your
8  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  General Public License for more details.
14
15  You should have received a copy of the GNU General Public License
16  along with GNUnet; see the file COPYING.  If not, write to the
17  Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18  Boston, MA 02111-1307, USA.
19  */
20 /**
21  * @file ats-tests/ats-testing-experiment.c
22  * @brief ats benchmark: controlled experiment execution
23  * @author Christian Grothoff
24  * @author Matthias Wachs
25  */
26 #include "platform.h"
27 #include "gnunet_util_lib.h"
28 #include "gnunet_ats_plugin.h"
29 #include "gnunet_ats_service.h"
30 #include "gnunet-service-ats_addresses.h"
31 #include "gnunet-service-ats_normalization.h"
32 #include "test_ats_api_common.h"
33
34 enum GeneratorType
35 {
36   GNUNET_ATS_TEST_TG_LINEAR,
37   GNUNET_ATS_TEST_TG_CONSTANT,
38   GNUNET_ATS_TEST_TG_RANDOM,
39   GNUNET_ATS_TEST_TG_SINUS
40 };
41
42
43 enum OperationType
44 {
45   SOLVER_OP_ADD_ADDRESS,
46   SOLVER_OP_DEL_ADDRESS,
47   SOLVER_OP_START_SET_PROPERTY,
48   SOLVER_OP_STOP_SET_PROPERTY,
49   SOLVER_OP_START_SET_PREFERENCE,
50   SOLVER_OP_STOP_SET_PREFERENCE
51 };
52
53 struct Episode;
54
55 struct Experiment;
56
57 typedef void (*GNUNET_ATS_TESTING_EpisodeDoneCallback) (
58     struct Episode *e);
59
60 typedef void (*GNUNET_ATS_TESTING_ExperimentDoneCallback) (struct Experiment *e,
61     struct GNUNET_TIME_Relative duration,int success);
62
63 /**
64  * An operation in an experiment
65  */
66 struct GNUNET_ATS_TEST_Operation
67 {
68   struct GNUNET_ATS_TEST_Operation *next;
69   struct GNUNET_ATS_TEST_Operation *prev;
70
71   long long unsigned int address_id;
72   long long unsigned int peer_id;
73   long long unsigned int address_session;
74   long long unsigned int address_network;
75   char*address;
76   char*plugin;
77
78   long long unsigned int base_rate;
79   long long unsigned int max_rate;
80   struct GNUNET_TIME_Relative period;
81   struct GNUNET_TIME_Relative frequency;
82
83   enum OperationType type;
84   enum GeneratorType tg_type;
85   enum GNUNET_ATS_PreferenceKind pref_type;
86 };
87
88 struct Episode
89 {
90   int id;
91   struct Episode *next;
92   struct GNUNET_TIME_Relative duration;
93
94   struct GNUNET_ATS_TEST_Operation *head;
95   struct GNUNET_ATS_TEST_Operation *tail;
96 };
97
98
99 struct Experiment
100 {
101   char *name;
102   char *cfg_file;
103   unsigned long long int num_masters;
104   unsigned long long int num_slaves;
105   struct GNUNET_TIME_Relative log_freq;
106   struct GNUNET_TIME_Relative max_duration;
107   struct GNUNET_TIME_Relative total_duration;
108   struct GNUNET_TIME_Absolute start_time;
109   unsigned int num_episodes;
110   struct Episode *start;
111
112   struct GNUNET_CONFIGURATION_Handle *cfg;
113
114   GNUNET_SCHEDULER_TaskIdentifier experiment_timeout_task;
115   GNUNET_SCHEDULER_TaskIdentifier episode_timeout_task;
116   struct Episode *cur;
117
118   GNUNET_ATS_TESTING_EpisodeDoneCallback ep_done_cb;
119   GNUNET_ATS_TESTING_ExperimentDoneCallback e_done_cb;
120 };
121
122
123 /**
124  * A single logging time step for a partner
125  */
126 struct PartnerLoggingTimestep
127 {
128   /**
129    * Peer
130    */
131   struct BenchmarkPeer *slave;
132
133   /**
134    * Total number of messages this peer has sent
135    */
136   unsigned int total_messages_sent;
137
138   /**
139    * Total number of bytes this peer has sent
140    */
141   unsigned int total_bytes_sent;
142
143   /**
144    * Total number of messages this peer has received
145    */
146   unsigned int total_messages_received;
147
148   /**
149    * Total number of bytes this peer has received
150    */
151   unsigned int total_bytes_received;
152
153   /**
154    * Total outbound throughput for master in Bytes / s
155    */
156   unsigned int throughput_sent;
157
158   /**
159    * Total inbound throughput for master in Bytes / s
160    */
161   unsigned int throughput_recv;
162
163   /**
164    * Accumulated RTT for all messages
165    */
166   unsigned int total_app_rtt;
167
168   /**
169    * Current application level delay
170    */
171   unsigned int app_rtt;
172
173   /* Current ATS properties */
174
175   uint32_t ats_distance;
176
177   uint32_t ats_delay;
178
179   uint32_t bandwidth_in;
180
181   uint32_t bandwidth_out;
182
183   uint32_t ats_utilization_up;
184
185   uint32_t ats_utilization_down;
186
187   uint32_t ats_network_type;
188
189   uint32_t ats_cost_wan;
190
191   uint32_t ats_cost_lan;
192
193   uint32_t ats_cost_wlan;
194
195   double pref_bandwidth;
196   double pref_delay;
197 };
198
199
200 /**
201  * A single logging time step for a peer
202  */
203 struct PeerLoggingTimestep
204 {
205   /**
206    * Next in DLL
207    */
208   struct PeerLoggingTimestep *next;
209
210   /**
211    * Prev in DLL
212    */
213   struct PeerLoggingTimestep *prev;
214
215   /**
216    * Logging timestamp
217    */
218   struct GNUNET_TIME_Absolute timestamp;
219
220   /**
221    * Total number of messages this peer has sent
222    */
223   unsigned int total_messages_sent;
224
225   /**
226    * Total number of bytes this peer has sent
227    */
228   unsigned int total_bytes_sent;
229
230   /**
231    * Total number of messages this peer has received
232    */
233   unsigned int total_messages_received;
234
235   /**
236    * Total number of bytes this peer has received
237    */
238   unsigned int total_bytes_received;
239
240   /**
241    * Total outbound throughput for master in Bytes / s
242    */
243   unsigned int total_throughput_send;
244
245   /**
246    * Total inbound throughput for master in Bytes / s
247    */
248   unsigned int total_throughput_recv;
249
250   /**
251    * Logs for slaves
252    */
253   struct PartnerLoggingTimestep *slaves_log;
254 };
255
256 /**
257  * Entry for a benchmark peer
258  */
259 struct LoggingPeer
260 {
261   /**
262    * Peer
263    */
264   struct BenchmarkPeer *peer;
265
266   /**
267    * Start time
268    */
269   struct GNUNET_TIME_Absolute start;
270
271   /**
272    * DLL for logging entries: head
273    */
274   struct PeerLoggingTimestep *head;
275
276   /**
277    * DLL for logging entries: tail
278    */
279   struct PeerLoggingTimestep *tail;
280 };
281
282
283 struct LoggingHandle
284 {
285   /**
286    * Logging task
287    */
288   GNUNET_SCHEDULER_TaskIdentifier log_task;
289
290   /**
291    * Reference to perf_ats' masters
292    */
293   int num_masters;
294   int num_slaves;
295   int running;
296   int verbose;
297   char *name;
298   struct GNUNET_TIME_Relative frequency;
299
300   /**
301    * Log structure of length num_peers
302    */
303   struct LoggingPeer *lp;
304 };
305
306
307 /**
308  * Start logging
309  *
310  * @param log_frequency the logging frequency
311  * @param testname the testname
312  * @param masters the master peers used for benchmarking
313  * @param num_master the number of master peers
314  * @return the logging handle or NULL on error
315  */
316 struct LoggingHandle *
317 GNUNET_ATS_TEST_logging_start(struct GNUNET_TIME_Relative log_frequency,
318     char *testname, struct BenchmarkPeer *masters, int num_masters, int num_slaves,
319     int verbose);
320
321 /**
322  * Stop logging
323  *
324  * @param l the logging handle
325  */
326 void
327 GNUNET_ATS_TEST_logging_clean_up (struct LoggingHandle *l);
328
329 /**
330  * Stop logging
331  *
332  * @param l the logging handle
333  */
334 void
335 GNUNET_ATS_TEST_logging_stop (struct LoggingHandle *l);
336
337 /**
338  * Log all data now
339  *
340  * @param l logging handle to use
341  */
342 void
343 GNUNET_ATS_TEST_logging_now (struct LoggingHandle *l);
344
345
346 /**
347  * Write logging data to file
348  *
349  * @param l logging handle to use
350  * @param test_name name of the current test
351  * @param plots create gnuplots: GNUNET_YES or GNUNET_NO
352  */
353 void
354 GNUNET_ATS_TEST_logging_write_to_file (struct LoggingHandle *l,
355     char *test_name, int plots);
356
357
358
359
360
361
362 /* LEGACY */
363
364 #if 0
365 #define TEST_ATS_PREFERENCE_DEFAULT 1.0
366
367 /**
368  * Message type sent for traffic generation
369  */
370 #define TEST_MESSAGE_TYPE_PING 12345
371
372 /**
373  * Message type sent as response during traffic generation
374  */
375 #define TEST_MESSAGE_TYPE_PONG 12346
376
377 /**
378  * Size of test messages
379  */
380 #define TEST_MESSAGE_SIZE 100
381
382 struct BenchmarkPartner;
383
384 struct BenchmarkPeer;
385
386 struct GNUNET_ATS_TEST_Topology;
387
388 struct TrafficGenerator;
389
390
391
392
393
394 /**
395  * Callback to call when topology setup is completed
396  *
397  * @param cls the closure
398  * @param masters array of master peers
399  * @param slaves array of master peers
400  */
401 typedef void (*GNUNET_ATS_TEST_TopologySetupDoneCallback) (void *cls,
402     struct BenchmarkPeer *masters,
403     struct BenchmarkPeer *slaves);
404
405 /**
406  * Callback called when logging is required for the data contained
407  *
408  * @param cls the closure
409  * @param address an address
410  * @param address_active is address active
411  * @param bandwidth_out bandwidth outbound
412  * @param bandwidth_in bandwidth inbound
413  * @param ats ats information
414  * @param ats_count number of ats inforation
415  */
416 typedef void
417 (*GNUNET_ATS_TEST_LogRequest) (void *cls,
418     const struct GNUNET_HELLO_Address *address,
419     int address_active,
420     struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out,
421     struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in,
422     const struct GNUNET_ATS_Information *ats,
423     uint32_t ats_count);
424
425 /**
426  * Information we track for a peer in the testbed.
427  */
428 struct BenchmarkPeer
429 {
430   /**
431    * Handle with testbed.
432    */
433   struct GNUNET_TESTBED_Peer *peer;
434
435   /**
436    * Unique identifier
437    */
438   int no;
439
440   /**
441    * Is this peer a measter: GNUNET_YES/GNUNET_NO
442    */
443   int master;
444
445   /**
446    *  Peer ID
447    */
448   struct GNUNET_PeerIdentity id;
449
450   /**
451    * Testbed operation to get peer information
452    */
453   struct GNUNET_TESTBED_Operation *peer_id_op;
454
455   /**
456    * Testbed operation to connect to ATS performance service
457    */
458   struct GNUNET_TESTBED_Operation *ats_perf_op;
459
460   /**
461    * Testbed operation to connect to core
462    */
463   struct GNUNET_TESTBED_Operation *comm_op;
464
465   /**
466    * ATS performance handle
467    */
468   struct GNUNET_ATS_PerformanceHandle *ats_perf_handle;
469
470   /**
471    * Masters only:
472    * Testbed connect operations to connect masters to slaves
473    */
474   struct TestbedConnectOperation *core_connect_ops;
475
476   /**
477    *  Core handle
478    */
479   struct GNUNET_CORE_Handle *ch;
480
481   /**
482    *  Core handle
483    */
484   struct GNUNET_TRANSPORT_Handle *th;
485
486   /**
487    * Masters only:
488    * Peer to set ATS preferences for
489    */
490   struct BenchmarkPeer *pref_partner;
491
492   /**
493    * Masters only
494    * Progress task
495    */
496   GNUNET_SCHEDULER_TaskIdentifier ats_task;
497
498   /**
499    * Masters only
500    * Progress task
501    */
502   double pref_value;
503
504   /**
505    * Array of partners with num_slaves entries (if master) or
506    * num_master entries (if slave)
507    */
508   struct BenchmarkPartner *partners;
509
510   /**
511    * Number of partners
512    */
513   int num_partners;
514
515   /**
516    * Number of core connections
517    */
518   int core_connections;
519
520   /**
521    * Masters only:
522    * Number of connections to slave peers
523    */
524   int core_slave_connections;
525
526   /**
527    * Total number of messages this peer has sent
528    */
529   unsigned int total_messages_sent;
530
531   /**
532    * Total number of bytes this peer has sent
533    */
534   unsigned int total_bytes_sent;
535
536   /**
537    * Total number of messages this peer has received
538    */
539   unsigned int total_messages_received;
540
541   /**
542    * Total number of bytes this peer has received
543    */
544   unsigned int total_bytes_received;
545 };
546
547 struct TrafficGenerator
548 {
549   struct TrafficGenerator *prev;
550   struct TrafficGenerator *next;
551
552   enum GeneratorType type;
553
554   struct BenchmarkPeer *src;
555   struct BenchmarkPartner *dest;
556
557   long int base_rate;
558   long int max_rate;
559   struct GNUNET_TIME_Relative duration_period;
560
561   GNUNET_SCHEDULER_TaskIdentifier send_task;
562   struct GNUNET_TIME_Absolute next_ping_transmission;
563   struct GNUNET_TIME_Absolute time_start;
564 };
565
566
567 struct PreferenceGenerator
568 {
569   struct PreferenceGenerator *prev;
570   struct PreferenceGenerator *next;
571
572   enum GeneratorType type;
573
574   struct BenchmarkPeer *src;
575   struct BenchmarkPartner *dest;
576
577   enum GNUNET_ATS_PreferenceKind kind;
578
579   long int base_value;
580   long int max_value;
581   struct GNUNET_TIME_Relative duration_period;
582   struct GNUNET_TIME_Relative frequency;
583
584   GNUNET_SCHEDULER_TaskIdentifier set_task;
585   struct GNUNET_TIME_Absolute next_ping_transmission;
586   struct GNUNET_TIME_Absolute time_start;
587 };
588
589 /**
590  * Information about a benchmarking partner
591  */
592 struct BenchmarkPartner
593 {
594   /**
595    * The peer itself this partner belongs to
596    */
597   struct BenchmarkPeer *me;
598
599   /**
600    * The partner peer
601    */
602   struct BenchmarkPeer *dest;
603
604   /**
605    * Core transmit handles
606    */
607   struct GNUNET_CORE_TransmitHandle *cth;
608
609   /**
610    * Transport transmit handles
611    */
612   struct GNUNET_TRANSPORT_TransmitHandle *tth;
613
614   struct TrafficGenerator *tg;
615   struct PreferenceGenerator *pg;
616
617   /**
618    * Timestamp to calculate communication layer delay
619    */
620   struct GNUNET_TIME_Absolute last_message_sent;
621
622   /**
623    * Accumulated RTT for all messages
624    */
625   unsigned int total_app_rtt;
626
627   /**
628    * Number of messages sent to this partner
629    */
630   unsigned int messages_sent;
631
632   /**
633    * Number of bytes sent to this partner
634    */
635   unsigned int bytes_sent;
636
637   /**
638    * Number of messages received from this partner
639    */
640   unsigned int messages_received;
641
642   /**
643    * Number of bytes received from this partner
644    */
645   unsigned int bytes_received;
646
647   /* Current ATS properties */
648
649   uint32_t ats_distance;
650
651   uint32_t ats_delay;
652
653   uint32_t bandwidth_in;
654
655   uint32_t bandwidth_out;
656
657   uint32_t ats_utilization_up;
658
659   uint32_t ats_utilization_down;
660
661   uint32_t ats_network_type;
662
663   uint32_t ats_cost_wan;
664
665   uint32_t ats_cost_lan;
666
667   uint32_t ats_cost_wlan;
668
669   double pref_bandwidth;
670   double pref_delay;
671 };
672
673 /**
674  * Overall state of the performance benchmark
675  */
676 struct BenchmarkState
677 {
678   /**
679    * Are we connected to ATS service of all peers: GNUNET_YES/NO
680    */
681   int connected_ATS_service;
682
683   /**
684    * Are we connected to CORE service of all peers: GNUNET_YES/NO
685    */
686   int connected_COMM_service;
687
688   /**
689    * Are we connected to all peers: GNUNET_YES/NO
690    */
691   int connected_PEERS;
692
693   /**
694    * Are we connected to all slave peers on CORE level: GNUNET_YES/NO
695    */
696   int connected_CORE;
697
698   /**
699    * Are we connected to CORE service of all peers: GNUNET_YES/NO
700    */
701   int benchmarking;
702 };
703
704
705 struct GNUNET_ATS_TEST_Topology
706 {
707   /**
708    * Shutdown task
709    */
710   GNUNET_SCHEDULER_TaskIdentifier shutdown_task;
711
712   /**
713    * Progress task
714    */
715   GNUNET_SCHEDULER_TaskIdentifier progress_task;
716
717   /**
718    * Test result
719    */
720   int result;
721
722   /**Test core (GNUNET_YES) or transport (GNUNET_NO)
723    */
724   int test_core;
725
726   /**
727    * Solver string
728    */
729   char *solver;
730
731   /**
732    * Preference string
733    */
734   char *testname;
735
736   /**
737    * Preference string
738    */
739   char *pref_str;
740
741   /**
742    * ATS preference value
743    */
744   int pref_val;
745
746   /**
747    * Number master peers
748    */
749   unsigned int num_masters;
750
751   /**
752    * Array of master peers
753    */
754   struct BenchmarkPeer *mps;
755
756   /**
757    * Number slave peers
758    */
759   unsigned int num_slaves;
760
761   /**
762    * Array of slave peers
763    */
764   struct BenchmarkPeer *sps;
765
766   /**
767    * Benchmark duration
768    */
769   struct GNUNET_TIME_Relative perf_duration;
770
771   /**
772    * Logging frequency
773    */
774   struct GNUNET_TIME_Relative log_frequency;
775
776   /**
777    * Benchmark state
778    */
779   struct BenchmarkState state;
780
781   struct GNUNET_CORE_MessageHandler *handlers;
782
783   GNUNET_TRANSPORT_ReceiveCallback transport_recv_cb;
784
785   GNUNET_ATS_TEST_TopologySetupDoneCallback done_cb;
786   GNUNET_ATS_AddressInformationCallback ats_perf_cb;
787   void *done_cb_cls;
788 };
789
790
791
792 /*
793  * Experiment related functions
794  */
795
796
797 /**
798  * Execute the specified experiment
799  *
800  * @param e the Experiment
801  * @param ep_done_cb a episode is completed
802  * @param e_done_cb the experiment is completed
803  */
804 void
805 GNUNET_ATS_TEST_experimentation_run (struct Experiment *e,
806     GNUNET_ATS_TESTING_EpisodeDoneCallback ep_done_cb,
807     GNUNET_ATS_TESTING_ExperimentDoneCallback e_done_cb);
808
809 /**
810  * Load an experiment from a file
811  *
812  * @param filename the file
813  * @return the Experiment or NULL on failure
814  */
815 struct Experiment *
816 GNUNET_ATS_TEST_experimentation_load (char *filename);
817
818
819 /**
820  * Stop an experiment
821  *
822  * @param e the experiment
823  */
824 void
825 GNUNET_ATS_TEST_experimentation_stop (struct Experiment *e);
826
827 /*
828  * Traffic related functions
829  */
830
831 void
832 GNUNET_ATS_TEST_traffic_handle_ping (struct BenchmarkPartner *p);
833
834 void
835 GNUNET_ATS_TEST_traffic_handle_pong (struct BenchmarkPartner *p);
836
837
838 /**
839  * Generate between the source master and the partner and send traffic with a
840  * maximum rate.
841  *
842  * @param src traffic source
843  * @param dest traffic partner
844  * @param type type of traffic to generate
845  * @param base_rate traffic base rate to send data with
846  * @param max_rate  traffic maximum rate to send data with
847  * @param period duration of a period of traffic generation (~ 1/frequency)
848  * @param duration how long to generate traffic
849  * @return the traffic generator
850  */
851 struct TrafficGenerator *
852 GNUNET_ATS_TEST_generate_traffic_start (struct BenchmarkPeer *src,
853     struct BenchmarkPartner *dest,
854     enum GeneratorType type,
855     long int base_rate,
856     long int max_rate,
857     struct GNUNET_TIME_Relative period,
858     struct GNUNET_TIME_Relative duration);
859
860 void
861 GNUNET_ATS_TEST_generate_traffic_stop (struct TrafficGenerator *tg);
862
863 /**
864  * Stop all traffic generators
865  */
866 void
867 GNUNET_ATS_TEST_generate_traffic_stop_all ();
868
869 struct PreferenceGenerator *
870 GNUNET_ATS_TEST_generate_preferences_start (struct BenchmarkPeer *src,
871     struct BenchmarkPartner *dest,
872     enum GeneratorType type,
873     long int base_value,
874     long int value_rate,
875     struct GNUNET_TIME_Relative period,
876     struct GNUNET_TIME_Relative frequency,
877     enum GNUNET_ATS_PreferenceKind kind);
878
879 void
880 GNUNET_ATS_TEST_generate_preferences_stop (struct PreferenceGenerator *pg);
881
882 void
883 GNUNET_ATS_TEST_generate_preferences_stop_all ();
884
885 /*
886  * Logging related functions
887  */
888
889
890
891 /*
892  * Topology related functions
893  */
894
895 struct BenchmarkPeer *
896 GNUNET_ATS_TEST_get_peer (int src);
897
898 struct BenchmarkPartner *
899 GNUNET_ATS_TEST_get_partner (int src, int dest);
900
901 /**
902  * Create a topology for ats testing
903  *
904  * @param name test name
905  * @param cfg_file configuration file to use for the peers
906  * @param num_slaves number of slaves
907  * @param num_masters number of masters
908  * @param test_core connect to CORE service (GNUNET_YES) or transport (GNUNET_NO)
909  * @param done_cb function to call when topology is setup
910  * @param done_cb_cls cls for callback
911  * @param recv_cb callback to call when data are received
912  * @param perf_cb callback to call when performance info are received
913  */
914 void
915 GNUNET_ATS_TEST_create_topology (char *name, char *cfg_file,
916     unsigned int num_slaves,
917     unsigned int num_masters,
918     int test_core,
919     GNUNET_ATS_TEST_TopologySetupDoneCallback done_cb,
920     void *done_cb_cls,
921     GNUNET_TRANSPORT_ReceiveCallback recv_cb,
922     GNUNET_ATS_TEST_LogRequest ats_perf_cb);
923
924 /**
925  * Shutdown topology
926  */
927 void
928 GNUNET_ATS_TEST_shutdown_topology (void);
929 #endif
930 /* end of file ats-testing.h */