arg
[oweals/gnunet.git] / src / fs / test_gnunet_service_fs_migration.c
1 /*
2      This file is part of GNUnet.
3      (C) 2010 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 /**
22  * @file fs/test_gnunet_service_fs_migration.c
23  * @brief test content migration between two peers
24  * @author Christian Grothoff
25  */
26 #include "platform.h"
27 #include "fs_test_lib.h"
28 #include "gnunet_testing_lib.h"
29
30 #define VERBOSE GNUNET_NO
31
32 /**
33  * File-size we use for testing.
34  */
35 #define FILESIZE (2 * 32 * 1024)
36
37 /**
38  * How long until we give up on transmitting the message?
39  */
40 #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120)
41
42 /**
43  * How long do we give the peers for content migration?
44  */
45 #define MIGRATION_DELAY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15)
46
47 #define SEED 42
48
49 static struct GNUNET_FS_TestDaemon *daemons[2];
50
51 static int ok;
52
53 static struct GNUNET_TIME_Absolute start_time;
54
55 static void
56 do_stop (void *cls,
57          const struct GNUNET_SCHEDULER_TaskContext *tc)
58 {
59   struct GNUNET_TIME_Relative del;
60   char *fancy;
61
62   GNUNET_FS_TEST_daemons_stop (2,
63                                daemons);
64   if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE))
65     {
66       del = GNUNET_TIME_absolute_get_duration (start_time);
67       if (del.rel_value == 0)
68         del.rel_value = 1;
69       fancy = GNUNET_STRINGS_byte_size_fancy (((unsigned long long)FILESIZE) * 1000LL / del.rel_value);
70       fprintf (stdout,
71                "Download speed was %s/s\n",
72                fancy);
73       GNUNET_free (fancy);
74       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
75                   "Finished download, shutting down\n",
76                   (unsigned long long) FILESIZE);
77     }
78   else
79     {
80       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
81                   "Timeout during download, shutting down with error\n");
82       ok = 1;
83     }
84 }
85
86
87 static void
88 do_download (void *cls,
89              const char *emsg)
90 {
91   struct GNUNET_FS_Uri *uri = cls;
92
93   if (emsg != NULL)
94     {
95       GNUNET_FS_TEST_daemons_stop (2,
96                                    daemons);
97       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
98                   "Failed to stop source daemon: %s\n",
99                   emsg);
100       GNUNET_FS_uri_destroy (uri);
101       ok = 1;
102       return;
103     }
104   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
105               "Downloading %llu bytes\n",
106               (unsigned long long) FILESIZE);
107   start_time = GNUNET_TIME_absolute_get ();
108   GNUNET_FS_TEST_download (daemons[0],
109                            TIMEOUT,
110                            1, SEED, uri, 
111                            VERBOSE, 
112                            &do_stop, NULL);
113   GNUNET_FS_uri_destroy (uri);
114 }
115
116
117 static void
118 stop_source_peer (void *cls,
119                   const struct GNUNET_SCHEDULER_TaskContext *tc)
120 {
121   struct GNUNET_FS_Uri *uri = cls;
122   struct GNUNET_TESTING_PeerGroup *pg;
123
124   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
125               "Stopping source peer\n");
126   pg = GNUNET_FS_TEST_get_group (daemons);
127   GNUNET_TESTING_daemons_vary (pg, 1, GNUNET_NO, TIMEOUT,
128                                &do_download,
129                                uri);
130 }
131
132
133 static void
134 do_wait (void *cls,
135          const struct GNUNET_FS_Uri *uri)
136 {
137   struct GNUNET_FS_Uri *d;
138
139   if (NULL == uri)
140     {
141       GNUNET_FS_TEST_daemons_stop (2,
142                                    daemons);
143       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
144                   "Timeout during upload attempt, shutting down with error\n");
145       ok = 1;
146       return;
147     }
148   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
149               "Waiting to allow content to migrate\n"); 
150   d = GNUNET_FS_uri_dup (uri);
151   (void) GNUNET_SCHEDULER_add_delayed (MIGRATION_DELAY,
152                                        &stop_source_peer,
153                                        d);
154 }
155
156
157 static void
158 do_publish (void *cls,
159             const struct GNUNET_SCHEDULER_TaskContext *tc)
160 {
161   if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE))
162     {
163       GNUNET_FS_TEST_daemons_stop (2,
164                                    daemons);
165       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
166                   "Timeout during connect attempt, shutting down with error\n");
167       ok = 1;
168       return;
169     }
170   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
171               "Publishing %llu bytes\n",
172               (unsigned long long) FILESIZE);
173   GNUNET_FS_TEST_publish (daemons[1],
174                           TIMEOUT,
175                           1, GNUNET_NO, FILESIZE, SEED, 
176                           VERBOSE, 
177                           &do_wait, NULL);
178 }
179
180
181 static void
182 do_connect (void *cls,
183             const struct GNUNET_SCHEDULER_TaskContext *tc)
184 {
185   if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE))
186     {
187       fprintf (stderr,
188                "Daemons failed to start!\n");
189       GNUNET_break (0);
190       ok = 1;
191       return;
192     }
193   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
194               "Daemons started, will now try to connect them\n");
195   GNUNET_FS_TEST_daemons_connect (daemons[0],
196                                   daemons[1],
197                                   TIMEOUT,
198                                   &do_publish,
199                                   NULL);  
200 }
201
202
203 static void
204 run (void *cls,
205      char *const *args,
206      const char *cfgfile,
207      const struct GNUNET_CONFIGURATION_Handle *cfg)
208 {
209   GNUNET_FS_TEST_daemons_start ("test_gnunet_service_fs_migration_data.conf",
210                                 TIMEOUT,
211                                 2,
212                                 daemons,
213                                 &do_connect,
214                                 NULL);
215 }
216
217
218 int
219 main (int argc, char *argv[])
220 {
221   char *const argvx[] = { 
222     "test-gnunet-service-fs-migration",
223     "-c",
224     "fs_test_lib_data.conf",
225 #if VERBOSE
226     "-L", "DEBUG",
227 #endif
228     NULL
229   };
230   struct GNUNET_GETOPT_CommandLineOption options[] = {
231     GNUNET_GETOPT_OPTION_END
232   };
233
234   GNUNET_DISK_directory_remove ("/tmp/test-gnunet-service-fs-migration/");
235   GNUNET_log_setup ("test_gnunet_service_fs_migration", 
236 #if VERBOSE
237                     "DEBUG",
238 #else
239                     "WARNING",
240 #endif
241                     NULL);
242   GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1,
243                       argvx, "test-gnunet-service-fs-migration",
244                       "nohelp", options, &run, NULL);
245   GNUNET_DISK_directory_remove ("/tmp/test-gnunet-service-fs-migration/");
246   return ok;
247 }
248
249 /* end of test_gnunet_service_fs_migration.c */