aboutsummaryrefslogtreecommitdiff
path: root/src/ats/gnunet-service-ats_addresses_simplistic.c
diff options
context:
space:
mode:
authorMatthias Wachs <wachs@net.in.tum.de>2012-12-05 14:06:58 +0000
committerMatthias Wachs <wachs@net.in.tum.de>2012-12-05 14:06:58 +0000
commitc5c7f5a17498e46fd185261bca847aad844c7cd4 (patch)
treea65ae02cddcadde6151d283428db9c26ff262f58 /src/ats/gnunet-service-ats_addresses_simplistic.c
parent6aa0b9eb1b7bed77d8c4a7727a7f66c52439167f (diff)
downloadgnunet-c5c7f5a17498e46fd185261bca847aad844c7cd4.tar.gz
gnunet-c5c7f5a17498e46fd185261bca847aad844c7cd4.zip
commit required ... things can be broken
Diffstat (limited to 'src/ats/gnunet-service-ats_addresses_simplistic.c')
-rw-r--r--src/ats/gnunet-service-ats_addresses_simplistic.c176
1 files changed, 170 insertions, 6 deletions
diff --git a/src/ats/gnunet-service-ats_addresses_simplistic.c b/src/ats/gnunet-service-ats_addresses_simplistic.c
index 62d996117..ff2933a59 100644
--- a/src/ats/gnunet-service-ats_addresses_simplistic.c
+++ b/src/ats/gnunet-service-ats_addresses_simplistic.c
@@ -29,13 +29,17 @@
29#include "gnunet-service-ats_addresses.h" 29#include "gnunet-service-ats_addresses.h"
30#include "gnunet_statistics_service.h" 30#include "gnunet_statistics_service.h"
31 31
32#define LOG(kind,...) GNUNET_log_from (kind, "ats-simplistic",__VA_ARGS__)
32 33
33/** 34/**
34 * A handle for the simplistic solver 35 * A handle for the simplistic solver
35 */ 36 */
36struct GAS_SIMPLISTIC_Handle 37struct GAS_SIMPLISTIC_Handle
37{ 38{
38 39 unsigned int active_addresses;
40 int *quota_net;
41 unsigned long long *quota_in;
42 unsigned long long *quota_out;
39}; 43};
40 44
41 45
@@ -48,9 +52,23 @@ struct GAS_SIMPLISTIC_Handle
48 */ 52 */
49void * 53void *
50GAS_simplistic_init (const struct GNUNET_CONFIGURATION_Handle *cfg, 54GAS_simplistic_init (const struct GNUNET_CONFIGURATION_Handle *cfg,
51 const struct GNUNET_STATISTICS_Handle *stats) 55 const struct GNUNET_STATISTICS_Handle *stats,
56 int *network,
57 unsigned long long *out_dest,
58 unsigned long long *in_dest,
59 int dest_length)
52{ 60{
53 struct GAS_SIMPLISTIC_Handle *solver = GNUNET_malloc (sizeof (struct GAS_SIMPLISTIC_Handle)); 61 struct GAS_SIMPLISTIC_Handle *solver = GNUNET_malloc (sizeof (struct GAS_SIMPLISTIC_Handle));
62
63 solver->quota_net = GNUNET_malloc (dest_length * sizeof (int));
64 memcpy (solver->quota_net, network, dest_length * sizeof (int));
65
66 solver->quota_in = GNUNET_malloc (dest_length * sizeof (unsigned long long));
67 memcpy (solver->quota_in, out_dest, dest_length * sizeof (int));
68
69 solver->quota_out = GNUNET_malloc (dest_length * sizeof (unsigned long long));
70 memcpy (solver->quota_out, out_dest, dest_length * sizeof (unsigned long long));
71
54 return solver; 72 return solver;
55} 73}
56 74
@@ -63,8 +81,12 @@ GAS_simplistic_init (const struct GNUNET_CONFIGURATION_Handle *cfg,
63void 81void
64GAS_simplistic_done (void *solver) 82GAS_simplistic_done (void *solver)
65{ 83{
66 GNUNET_assert (solver != NULL); 84 struct GAS_SIMPLISTIC_Handle *s = solver;
67 GNUNET_free (solver); 85 GNUNET_assert (s != NULL);
86 GNUNET_free (s->quota_net);
87 GNUNET_free (s->quota_in);
88 GNUNET_free (s->quota_out);
89 GNUNET_free (s);
68} 90}
69 91
70/** 92/**
@@ -95,6 +117,128 @@ GAS_simplistic_address_delete (void *solver, struct GNUNET_CONTAINER_MultiHashMa
95} 117}
96 118
97 119
120
121/**
122 * Find a "good" address to use for a peer. If we already have an existing
123 * address, we stick to it. Otherwise, we pick by lowest distance and then
124 * by lowest latency.
125 *
126 * @param cls the 'struct ATS_Address**' where we store the result
127 * @param key unused
128 * @param value another 'struct ATS_Address*' to consider using
129 * @return GNUNET_OK (continue to iterate)
130 */
131static int
132find_address_it (void *cls, const struct GNUNET_HashCode * key, void *value)
133{
134 struct ATS_Address **previous_p = cls;
135 struct ATS_Address *current = (struct ATS_Address *) value;
136 struct ATS_Address *previous = *previous_p;
137 struct GNUNET_TIME_Absolute now;
138
139 now = GNUNET_TIME_absolute_get();
140
141 if (current->blocked_until.abs_value == GNUNET_TIME_absolute_max (now, current->blocked_until).abs_value)
142 {
143 /* This address is blocked for suggestion */
144 LOG (GNUNET_ERROR_TYPE_DEBUG,
145 "Address %p blocked for suggestion for %llu ms \n",
146 current,
147 GNUNET_TIME_absolute_get_difference(now, current->blocked_until).rel_value);
148 return GNUNET_OK;
149 }
150
151 current->block_interval = GNUNET_TIME_relative_add (current->block_interval, ATS_BLOCKING_DELTA);
152 current->blocked_until = GNUNET_TIME_absolute_add (now, current->block_interval);
153
154 LOG (GNUNET_ERROR_TYPE_DEBUG,
155 "Address %p ready for suggestion, block interval now %llu \n",
156 current, current->block_interval);
157
158 if (NULL != previous)
159 {
160 if ((0 == strcmp (previous->plugin, "tcp")) &&
161 (0 == strcmp (current->plugin, "tcp")))
162 {
163 if ((0 != previous->addr_len) &&
164 (0 == current->addr_len))
165 {
166 /* saved address was an outbound address, but we have an inbound address */
167 *previous_p = current;
168 return GNUNET_OK;
169 }
170 if (0 == previous->addr_len)
171 {
172 /* saved address was an inbound address, so do not overwrite */
173 return GNUNET_OK;
174 }
175 }
176 }
177
178 if (NULL == previous)
179 {
180 *previous_p = current;
181 return GNUNET_OK;
182 }
183 if ((ntohl (previous->assigned_bw_in.value__) == 0) &&
184 (ntohl (current->assigned_bw_in.value__) > 0))
185 {
186 /* stick to existing connection */
187 *previous_p = current;
188 return GNUNET_OK;
189 }
190 if (previous->atsp_distance > current->atsp_distance)
191 {
192 /* user shorter distance */
193 *previous_p = current;
194 return GNUNET_OK;
195 }
196 if (previous->atsp_latency.rel_value > current->atsp_latency.rel_value)
197 {
198 /* user lower latency */
199 *previous_p = current;
200 return GNUNET_OK;
201 }
202 /* don't care */
203 return GNUNET_OK;
204}
205
206static int
207update_bw_simple_it (void *cls, const struct GNUNET_HashCode * key, void *value)
208{
209 struct GAS_SIMPLISTIC_Handle *s = cls;
210 struct ATS_Address *aa = value;
211
212 if (GNUNET_YES != aa->active)
213 return GNUNET_OK;
214 GNUNET_assert (s->active_addresses > 0);
215
216
217 /* Simple method */
218
219 aa->assigned_bw_in.value__ = htonl (UINT32_MAX / s->active_addresses);
220 aa->assigned_bw_out.value__ = htonl (UINT32_MAX / s->active_addresses);
221
222 //send_bw_notification (aa);
223
224 return GNUNET_OK;
225}
226
227/**
228 * Some (significant) input changed, recalculate bandwidth assignment
229 * for all peers.
230 */
231static void
232recalculate_assigned_bw (void *solver,
233 struct GNUNET_CONTAINER_MultiHashMap * addresses)
234{
235 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
236 "Recalculating bandwidth for all active connections\n");
237 GNUNET_CONTAINER_multihashmap_iterate (addresses, &update_bw_simple_it, solver);
238}
239
240
241
98/** 242/**
99 * Get the prefered address for a specific peer 243 * Get the prefered address for a specific peer
100 * 244 *
@@ -102,12 +246,32 @@ GAS_simplistic_address_delete (void *solver, struct GNUNET_CONTAINER_MultiHashMa
102 * @param addresses the address hashmap containing all addresses 246 * @param addresses the address hashmap containing all addresses
103 * @param peer the identity of the peer 247 * @param peer the identity of the peer
104 */ 248 */
105struct ATS_PreferedAddress * 249struct ATS_Address *
106GAS_simplistic_get_preferred_address (void *solver, 250GAS_simplistic_get_preferred_address (void *solver,
107 struct GNUNET_CONTAINER_MultiHashMap * addresses, 251 struct GNUNET_CONTAINER_MultiHashMap * addresses,
108 const struct GNUNET_PeerIdentity *peer) 252 const struct GNUNET_PeerIdentity *peer)
109{ 253{
110 return NULL; 254 struct GAS_SIMPLISTIC_Handle *s = solver;
255 struct ATS_Address *aa;
256
257 GNUNET_assert (s != NULL);
258 aa = NULL;
259 /* Get address with: stick to current address, lower distance, lower latency */
260 GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey,
261 &find_address_it, &aa);
262 if (NULL == aa)
263 LOG (GNUNET_ERROR_TYPE_DEBUG, "Cannot suggest address for peer `%s'\n", GNUNET_i2s (peer));
264 else
265 LOG (GNUNET_ERROR_TYPE_DEBUG, "Suggesting address %p for peer `%s'\n", aa, GNUNET_i2s (peer));
266
267 if (GNUNET_NO == aa->active)
268 {
269 aa->active = GNUNET_YES;
270 s->active_addresses++;
271 recalculate_assigned_bw (s, addresses);
272 }
273
274 return aa;
111} 275}
112 276
113 277