X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;f=src%2Fats%2Fgnunet-service-ats-new.c;h=d3b2f1ead72c6f539de72a5254a887571c8286ab;hb=08e22453a438c8a3f6135632a6ce39239b47d9f5;hp=57398e6413047720149e07e615605ad26d30cf78;hpb=e298fa7e3eeafea48a8abf6c5b8bf449b279e7a7;p=oweals%2Fgnunet.git diff --git a/src/ats/gnunet-service-ats-new.c b/src/ats/gnunet-service-ats-new.c index 57398e641..d3b2f1ead 100644 --- a/src/ats/gnunet-service-ats-new.c +++ b/src/ats/gnunet-service-ats-new.c @@ -20,11 +20,6 @@ * @brief ats service * @author Matthias Wachs * @author Christian Grothoff - * - * TODO: - * - implement messages ATS -> transport - * - implement loading / unloading of ATS plugins - * - expose plugin the API to send messages ATS -> transport */ #include "platform.h" #include "gnunet_util_lib.h" @@ -176,19 +171,97 @@ struct Client /** * Handle for statistics. */ -static struct GNUNET_STATISTICS_Handle *GSA_stats; +static struct GNUNET_STATISTICS_Handle *stats; /** * Our solver. */ static struct GNUNET_ATS_SolverFunctions *plugin; +/** + * Solver plugin name as string + */ +static char *plugin_name; + /** * The transport client (there can only be one at a time). */ static struct Client *transport_client; +/** + * Function called by the solver to prompt the transport to + * try out a new address. + * + * @param cls closure, NULL + * @param pid peer this is about + * @param address address the transport should try + */ +static void +suggest_cb (void *cls, + const struct GNUNET_PeerIdentity *pid, + const char *address) +{ + struct GNUNET_MQ_Envelope *env; + size_t slen = strlen (address) + 1; + struct AddressSuggestionMessage *as; + + if (NULL == transport_client) + { + // FIXME: stats! + return; + } + env = GNUNET_MQ_msg_extra (as, + slen, + GNUNET_MESSAGE_TYPE_ATS_ADDRESS_SUGGESTION); + as->peer = *pid; + memcpy (&as[1], + address, + slen); + GNUNET_MQ_send (transport_client->mq, + env); +} + + +/** + * Function called by the solver to tell the transpor to + * allocate bandwidth for the specified session. + * + * @param cls closure, NULL + * @param session session this is about + * @param peer peer this is about + * @param bw_in suggested bandwidth for receiving + * @param bw_out suggested bandwidth for transmission + */ +static void +allocate_cb (void *cls, + struct GNUNET_ATS_Session *session, + const struct GNUNET_PeerIdentity *peer, + struct GNUNET_BANDWIDTH_Value32NBO bw_in, + struct GNUNET_BANDWIDTH_Value32NBO bw_out) +{ + struct GNUNET_MQ_Envelope *env; + struct SessionAllocationMessage *sam; + + (void) cls; + if ( (NULL == transport_client) || + (session->client != transport_client) ) + { + /* transport must have just died and solver is addressing the + losses of sessions (possibly of previous transport), ignore! */ + return; + } + env = GNUNET_MQ_msg (sam, + GNUNET_MESSAGE_TYPE_ATS_SESSION_ALLOCATION); + sam->session_id = session->session_id; + sam->peer = *peer; + sam->bandwidth_in = bw_in; + sam->bandwidth_out = bw_out; + GNUNET_MQ_send (transport_client->mq, + env); +} + + /** * Convert @a properties to @a prop * @@ -359,7 +432,8 @@ handle_session_add (void *cls, const struct SessionAddMessage *message) { struct Client *c = cls; - struct GNUNET_ATS_Session *session; + const char *address = (const char *) &message[1]; + struct GNUNET_ATS_Session *session; int inbound_only = (GNUNET_MESSAGE_TYPE_ATS_SESSION_ADD_INBOUND_ONLY == ntohs (message->header.type)); @@ -385,12 +459,12 @@ handle_session_add (void *cls, session, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); session->sh = plugin->session_add (plugin->cls, - &session->data); + &session->data, + address); GNUNET_SERVICE_client_continue (c->client); } - /** * Handle 'session update' messages from transport clients. * @@ -572,11 +646,22 @@ cleanup_task (void *cls) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS shutdown initiated\n"); - if (NULL != GSA_stats) + if (NULL != stats) { - GNUNET_STATISTICS_destroy (GSA_stats, + GNUNET_STATISTICS_destroy (stats, GNUNET_NO); - GSA_stats = NULL; + stats = NULL; + } + if (NULL != plugin) + { + GNUNET_PLUGIN_unload (plugin_name, + plugin); + plugin = NULL; + } + if (NULL != plugin_name) + { + GNUNET_free (plugin_name); + plugin_name = NULL; } } @@ -593,19 +678,41 @@ run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, struct GNUNET_SERVICE_Handle *service) { - GSA_stats = GNUNET_STATISTICS_create ("ats", - cfg); + static struct GNUNET_ATS_PluginEnvironment env; + char *solver; + + stats = GNUNET_STATISTICS_create ("ats", + cfg); + if (GNUNET_SYSERR == + GNUNET_CONFIGURATION_get_value_string (cfg, + "ats", + "SOLVER", + &solver)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "No ATS solver configured, using 'simple' approach\n"); + solver = GNUNET_strdup ("simple"); + } GNUNET_SCHEDULER_add_shutdown (&cleanup_task, NULL); -#if 0 - if (GNUNET_OK != - GAS_plugin_init (cfg)) + env.cls = NULL; + env.cfg = cfg; + env.stats = stats; + env.suggest_cb = &suggest_cb; + env.allocate_cb = &allocate_cb; + GNUNET_asprintf (&plugin_name, + "libgnunet_plugin_ats2_%s", + solver); + GNUNET_free (solver); + if (NULL == (plugin = GNUNET_PLUGIN_load (plugin_name, + &env))) { - GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to initialize solver `%s'!\n"), + plugin_name); GNUNET_SCHEDULER_shutdown (); - return; + return; } -#endif }