aboutsummaryrefslogtreecommitdiff
path: root/src/dv/plugin_transport_dv.c
diff options
context:
space:
mode:
authorNathan S. Evans <evans@in.tum.de>2010-03-11 10:38:11 +0000
committerNathan S. Evans <evans@in.tum.de>2010-03-11 10:38:11 +0000
commit49da466bce647497cfc034db9e9761804e9d1a36 (patch)
tree65e289dcdb8c985ffa9ff4d243af6daeb83a6477 /src/dv/plugin_transport_dv.c
parente927f9bbf828bfc5038323c39aa3046ef948afe5 (diff)
downloadgnunet-49da466bce647497cfc034db9e9761804e9d1a36.tar.gz
gnunet-49da466bce647497cfc034db9e9761804e9d1a36.zip
shell for dv plugin and service, not yet working
Diffstat (limited to 'src/dv/plugin_transport_dv.c')
-rw-r--r--src/dv/plugin_transport_dv.c400
1 files changed, 400 insertions, 0 deletions
diff --git a/src/dv/plugin_transport_dv.c b/src/dv/plugin_transport_dv.c
new file mode 100644
index 000000000..aa25c97e6
--- /dev/null
+++ b/src/dv/plugin_transport_dv.c
@@ -0,0 +1,400 @@
1/*
2 This file is part of GNUnet
3 (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 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 2, 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 transport/plugin_transport_dv.c
23 * @brief DV transport service, takes incoming DV requests and deals with
24 * the DV service
25 * @author Christian Grothoff
26 */
27
28/**
29 * TODO:
30 *
31 * As a start, the dv plugin needs to listen for information from the dv
32 * service. The plugin (?) will be notified by core (?) when a tcp/udp/whatever
33 * message comes in that should be for dv. The plugin will then hand off the message
34 * to the dv service which will decrypt/validate the message (?) and then send the
35 * result back to us (the transport) which will then send the message to the transport
36 * service (yikes).
37 *
38 * Or, core will notify the dv service directly which will validate,
39 * etc. and then just send a message to us.
40 *
41 * For starters, this plugin needs to have a client which will listen for messages from
42 * the dv service that need to be sent up to the gnunet-transport-service.
43 *
44 * Messages sent from the dv transport get passed to the dv service which deals
45 * with the actual sending (how much state does this transport need? should it know
46 * which peers it is currently connected to and their distances, or just assume that
47 * anything should be passed along to the dv service?).
48 */
49#include "platform.h"
50#include "gnunet_protocols.h"
51#include "gnunet_connection_lib.h"
52#include "gnunet_server_lib.h"
53#include "gnunet_service_lib.h"
54#include "gnunet_statistics_service.h"
55#include "gnunet_dv_service.h"
56#include "gnunet_transport_service.h"
57#include "../transport/plugin_transport.h"
58#include "dv.h"
59
60#define DEBUG_TEMPLATE GNUNET_NO
61
62/**
63 * Encapsulation of all of the state of the plugin.
64 */
65struct Plugin;
66
67
68/**
69 * Session handle for connections.
70 */
71struct Session
72{
73
74 /**
75 * Stored in a linked list.
76 */
77 struct Session *next;
78
79 /**
80 * Pointer to the global plugin struct.
81 */
82 struct Plugin *plugin;
83
84 /**
85 * The client (used to identify this connection)
86 */
87 /* void *client; */
88
89 /**
90 * Continuation function to call once the transmission buffer
91 * has again space available. NULL if there is no
92 * continuation to call.
93 */
94 GNUNET_TRANSPORT_TransmitContinuation transmit_cont;
95
96 /**
97 * Closure for transmit_cont.
98 */
99 void *transmit_cont_cls;
100
101 /**
102 * To whom are we talking to (set to our identity
103 * if we are still waiting for the welcome message)
104 */
105 struct GNUNET_PeerIdentity sender;
106
107 /**
108 * At what time did we reset last_received last?
109 */
110 struct GNUNET_TIME_Absolute last_quota_update;
111
112 /**
113 * How many bytes have we received since the "last_quota_update"
114 * timestamp?
115 */
116 uint64_t last_received;
117
118 /**
119 * Number of bytes per ms that this peer is allowed
120 * to send to us.
121 */
122 uint32_t quota;
123
124};
125
126/**
127 * Encapsulation of all of the state of the plugin.
128 */
129struct Plugin
130{
131 /**
132 * Our environment.
133 */
134 struct GNUNET_TRANSPORT_PluginEnvironment *env;
135
136 /**
137 * List of open sessions.
138 */
139 struct Session *sessions;
140
141 /**
142 * Handle for the statistics service.
143 */
144 struct GNUNET_STATISTICS_Handle *statistics;
145
146 /**
147 * Our server.
148 */
149 struct GNUNET_SERVER_Handle *server;
150
151 /*
152 * Handle to the running service.
153 */
154 struct GNUNET_SERVICE_Context *service;
155
156 /**
157 * Copy of the handler array where the closures are
158 * set to this struct's instance.
159 */
160 struct GNUNET_SERVER_MessageHandler *handlers;
161
162 /**
163 * Handle to the DV service
164 */
165 struct GNUNET_DV_Handle *dv_handle;
166
167};
168
169
170void handle_dv_message_received (void *cls,
171 struct GNUNET_PeerIdentity *sender,
172 struct GNUNET_MessageHeader *msg,
173 unsigned int distance,
174 char *sender_address,
175 size_t sender_address_len)
176{
177 struct Plugin *plugin = cls;
178
179 plugin->env->receive(plugin,
180 sender,
181 msg,
182 distance,
183 sender_address,
184 sender_address_len);
185
186}
187
188
189/* Question: how does the transport service learn of a newly connected (gossipped about)
190 * DV peer? Should the plugin (here) create a HELLO for that peer and send it along,
191 * or should the DV service create a HELLO and send it to us via the other part?
192 */
193
194/**
195 * Function that can be used by the transport service to transmit
196 * a message using the plugin.
197 *
198 * @param cls closure
199 * @param target who should receive this message
200 * @param priority how important is the message
201 * @param msgbuf the message to transmit
202 * @param msgbuf_size number of bytes in 'msgbuf'
203 * @param timeout when should we time out
204 * @param addr the address to use (can be NULL if the plugin
205 * is "on its own" (i.e. re-use existing TCP connection))
206 * @param addrlen length of the address in bytes
207 * @param force_address GNUNET_YES if the plugin MUST use the given address,
208 * otherwise the plugin may use other addresses or
209 * existing connections (if available)
210 * @param cont continuation to call once the message has
211 * been transmitted (or if the transport is ready
212 * for the next transmission call; or if the
213 * peer disconnected...)
214 * @param cont_cls closure for cont
215 * @return number of bytes used (on the physical network, with overheads);
216 * -1 on hard errors (i.e. address invalid); 0 is a legal value
217 * and does NOT mean that the message was not transmitted (DV)
218 */
219static ssize_t
220dv_plugin_send (void *cls,
221 const struct GNUNET_PeerIdentity *target,
222 const char *msgbuf,
223 size_t msgbuf_size,
224 unsigned int priority,
225 struct GNUNET_TIME_Relative timeout,
226 const void *addr,
227 size_t addrlen,
228 int force_address,
229 GNUNET_TRANSPORT_TransmitContinuation
230 cont, void *cont_cls)
231{
232 int ret = 0;
233 struct Plugin *plugin = cls;
234
235 /* FIXME: do we want the dv plugin to remember sent messages to call continuation once message actually goes out?
236 * Or do we just call the continuation once we've notified the plugin?
237 */
238 ret = GNUNET_DV_send(plugin->dv_handle,
239 target,
240 msgbuf,
241 msgbuf_size,
242 priority,
243 timeout,
244 addr,
245 addrlen);
246 /*, cont, cont_cls);*/
247
248 if (ret == 0)
249 cont(cls, target, GNUNET_OK);
250 else
251 cont(cls, target, GNUNET_SYSERR);
252
253 return ret;
254}
255
256
257
258/**
259 * Function that can be used to force the plugin to disconnect
260 * from the given peer and cancel all previous transmissions
261 * (and their continuations).
262 *
263 * @param cls closure
264 * @param target peer from which to disconnect
265 */
266static void
267dv_plugin_disconnect (void *cls,
268 const struct GNUNET_PeerIdentity *target)
269{
270 // struct Plugin *plugin = cls;
271 // FIXME
272}
273
274
275/**
276 * Convert the transports address to a nice, human-readable
277 * format.
278 *
279 * @param cls closure
280 * @param type name of the transport that generated the address
281 * @param addr one of the addresses of the host, NULL for the last address
282 * the specific address format depends on the transport
283 * @param addrlen length of the address
284 * @param numeric should (IP) addresses be displayed in numeric form?
285 * @param timeout after how long should we give up?
286 * @param asc function to call on each string
287 * @param asc_cls closure for asc
288 */
289static void
290dv_plugin_address_pretty_printer (void *cls,
291 const char *type,
292 const void *addr,
293 size_t addrlen,
294 int numeric,
295 struct GNUNET_TIME_Relative timeout,
296 GNUNET_TRANSPORT_AddressStringCallback
297 asc, void *asc_cls)
298{
299 asc (asc_cls, NULL);
300}
301
302
303
304/**
305 * Another peer has suggested an address for this
306 * peer and transport plugin. Check that this could be a valid
307 * address. If so, consider adding it to the list
308 * of addresses.
309 *
310 * @param cls closure
311 * @param addr pointer to the address
312 * @param addrlen length of addr
313 * @return GNUNET_OK if this is a plausible address for this peer
314 * and transport
315 *
316 * FIXME: does this mean anything for the DV plugin?
317 */
318static int
319dv_plugin_address_suggested (void *cls,
320 void *addr, size_t addrlen)
321{
322 /* struct Plugin *plugin = cls; */
323
324 /* check if the address is plausible; if so,
325 add it to our list! */
326 return GNUNET_OK;
327}
328
329
330/**
331 * Entry point for the plugin.
332 */
333void *
334gnunet_plugin_transport_dv_init (void *cls)
335{
336 struct GNUNET_TRANSPORT_PluginEnvironment *env = cls;
337 struct GNUNET_TRANSPORT_PluginFunctions *api;
338 struct Plugin *plugin;
339 unsigned long long port;
340 struct GNUNET_SERVICE_Context *service;
341
342 service = GNUNET_SERVICE_start ("transport-dv", env->sched, env->cfg);
343 if (service == NULL)
344 {
345 GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING,
346 "dv",
347 _
348 ("Failed to start service for `%s' transport plugin.\n"),
349 "dv");
350 return NULL;
351 }
352
353 if ((GNUNET_OK !=
354 GNUNET_CONFIGURATION_get_value_number (env->cfg,
355 "transport-dv",
356 "PORT",
357 &port)))
358 {
359 GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR,
360 "dv",
361 _
362 ("Require valid port number for service `%s' in configuration!\n"),
363 "transport-dv");
364 GNUNET_SERVICE_stop (service);
365 return NULL;
366 }
367
368 plugin = GNUNET_malloc (sizeof (struct Plugin));
369 plugin->env = env;
370 plugin->statistics = NULL;
371 plugin->service = service;
372 plugin->server = GNUNET_SERVICE_get_server (service);
373
374 plugin->dv_handle = GNUNET_DV_connect(env->sched, env->cfg, &handle_dv_message_received, plugin);
375
376 api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions));
377 api->cls = plugin;
378 api->send = &dv_plugin_send;
379 api->disconnect = &dv_plugin_disconnect;
380 api->address_pretty_printer = &dv_plugin_address_pretty_printer;
381 api->check_address = &dv_plugin_address_suggested;
382 return api;
383}
384
385
386/**
387 * Exit point from the plugin.
388 */
389void *
390gnunet_plugin_transport_dv_done (void *cls)
391{
392 struct GNUNET_TRANSPORT_PluginFunctions *api = cls;
393 struct Plugin *plugin = api->cls;
394
395 GNUNET_free (plugin);
396 GNUNET_free (api);
397 return NULL;
398}
399
400/* end of plugin_transport_template.c */