aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/rc80211_pid_algo.c
diff options
context:
space:
mode:
authorHaavard Skinnemoen <haavard.skinnemoen@atmel.com>2008-10-23 09:24:10 -0400
committerHaavard Skinnemoen <haavard.skinnemoen@atmel.com>2008-10-23 09:24:10 -0400
commitd9214556b11a8d18ff588e60824c12041d30f791 (patch)
tree04ab59d13961675811a55c96fb12b2b167b72318 /net/mac80211/rc80211_pid_algo.c
parent72a1419a9d4c859a3345e4b83f8ef7d599d3818c (diff)
parente82c6106b04b85879d802bbbeaed30d9b10a92e2 (diff)
Merge branches 'boards' and 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/hskinnemoen/avr32-2.6
Diffstat (limited to 'net/mac80211/rc80211_pid_algo.c')
-rw-r--r--net/mac80211/rc80211_pid_algo.c191
1 files changed, 69 insertions, 122 deletions
diff --git a/net/mac80211/rc80211_pid_algo.c b/net/mac80211/rc80211_pid_algo.c
index a914ba73ccf5..86eb374e3b87 100644
--- a/net/mac80211/rc80211_pid_algo.c
+++ b/net/mac80211/rc80211_pid_algo.c
@@ -68,17 +68,14 @@
68 * exhibited a worse failed frames behaviour and we'll choose the highest rate 68 * exhibited a worse failed frames behaviour and we'll choose the highest rate
69 * whose failed frames behaviour is not worse than the one of the original rate 69 * whose failed frames behaviour is not worse than the one of the original rate
70 * target. While at it, check that the new rate is valid. */ 70 * target. While at it, check that the new rate is valid. */
71static void rate_control_pid_adjust_rate(struct ieee80211_local *local, 71static void rate_control_pid_adjust_rate(struct ieee80211_supported_band *sband,
72 struct sta_info *sta, int adj, 72 struct ieee80211_sta *sta,
73 struct rc_pid_sta_info *spinfo, int adj,
73 struct rc_pid_rateinfo *rinfo) 74 struct rc_pid_rateinfo *rinfo)
74{ 75{
75 struct ieee80211_sub_if_data *sdata;
76 struct ieee80211_supported_band *sband;
77 int cur_sorted, new_sorted, probe, tmp, n_bitrates, band; 76 int cur_sorted, new_sorted, probe, tmp, n_bitrates, band;
78 int cur = sta->txrate_idx; 77 int cur = spinfo->txrate_idx;
79 78
80 sdata = sta->sdata;
81 sband = local->hw.wiphy->bands[local->hw.conf.channel->band];
82 band = sband->band; 79 band = sband->band;
83 n_bitrates = sband->n_bitrates; 80 n_bitrates = sband->n_bitrates;
84 81
@@ -111,7 +108,7 @@ static void rate_control_pid_adjust_rate(struct ieee80211_local *local,
111 /* Fit the rate found to the nearest supported rate. */ 108 /* Fit the rate found to the nearest supported rate. */
112 do { 109 do {
113 if (rate_supported(sta, band, rinfo[tmp].index)) { 110 if (rate_supported(sta, band, rinfo[tmp].index)) {
114 sta->txrate_idx = rinfo[tmp].index; 111 spinfo->txrate_idx = rinfo[tmp].index;
115 break; 112 break;
116 } 113 }
117 if (adj < 0) 114 if (adj < 0)
@@ -121,9 +118,9 @@ static void rate_control_pid_adjust_rate(struct ieee80211_local *local,
121 } while (tmp < n_bitrates && tmp >= 0); 118 } while (tmp < n_bitrates && tmp >= 0);
122 119
123#ifdef CONFIG_MAC80211_DEBUGFS 120#ifdef CONFIG_MAC80211_DEBUGFS
124 rate_control_pid_event_rate_change( 121 rate_control_pid_event_rate_change(&spinfo->events,
125 &((struct rc_pid_sta_info *)sta->rate_ctrl_priv)->events, 122 spinfo->txrate_idx,
126 sta->txrate_idx, sband->bitrates[sta->txrate_idx].bitrate); 123 sband->bitrates[spinfo->txrate_idx].bitrate);
127#endif 124#endif
128} 125}
129 126
@@ -145,15 +142,11 @@ static void rate_control_pid_normalize(struct rc_pid_info *pinfo, int l)
145} 142}
146 143
147static void rate_control_pid_sample(struct rc_pid_info *pinfo, 144static void rate_control_pid_sample(struct rc_pid_info *pinfo,
148 struct ieee80211_local *local, 145 struct ieee80211_supported_band *sband,
149 struct sta_info *sta) 146 struct ieee80211_sta *sta,
147 struct rc_pid_sta_info *spinfo)
150{ 148{
151#ifdef CONFIG_MAC80211_MESH
152 struct ieee80211_sub_if_data *sdata = sta->sdata;
153#endif
154 struct rc_pid_sta_info *spinfo = sta->rate_ctrl_priv;
155 struct rc_pid_rateinfo *rinfo = pinfo->rinfo; 149 struct rc_pid_rateinfo *rinfo = pinfo->rinfo;
156 struct ieee80211_supported_band *sband;
157 u32 pf; 150 u32 pf;
158 s32 err_avg; 151 s32 err_avg;
159 u32 err_prop; 152 u32 err_prop;
@@ -162,9 +155,6 @@ static void rate_control_pid_sample(struct rc_pid_info *pinfo,
162 int adj, i, j, tmp; 155 int adj, i, j, tmp;
163 unsigned long period; 156 unsigned long period;
164 157
165 sband = local->hw.wiphy->bands[local->hw.conf.channel->band];
166 spinfo = sta->rate_ctrl_priv;
167
168 /* In case nothing happened during the previous control interval, turn 158 /* In case nothing happened during the previous control interval, turn
169 * the sharpening factor on. */ 159 * the sharpening factor on. */
170 period = (HZ * pinfo->sampling_period + 500) / 1000; 160 period = (HZ * pinfo->sampling_period + 500) / 1000;
@@ -180,14 +170,15 @@ static void rate_control_pid_sample(struct rc_pid_info *pinfo,
180 if (unlikely(spinfo->tx_num_xmit == 0)) 170 if (unlikely(spinfo->tx_num_xmit == 0))
181 pf = spinfo->last_pf; 171 pf = spinfo->last_pf;
182 else { 172 else {
173 /* XXX: BAD HACK!!! */
174 struct sta_info *si = container_of(sta, struct sta_info, sta);
175
183 pf = spinfo->tx_num_failed * 100 / spinfo->tx_num_xmit; 176 pf = spinfo->tx_num_failed * 100 / spinfo->tx_num_xmit;
184#ifdef CONFIG_MAC80211_MESH 177
185 if (pf == 100 && 178 if (ieee80211_vif_is_mesh(&si->sdata->vif) && pf == 100)
186 sdata->vif.type == IEEE80211_IF_TYPE_MESH_POINT) 179 mesh_plink_broken(si);
187 mesh_plink_broken(sta);
188#endif
189 pf <<= RC_PID_ARITH_SHIFT; 180 pf <<= RC_PID_ARITH_SHIFT;
190 sta->fail_avg = ((pf + (spinfo->last_pf << 3)) / 9) 181 si->fail_avg = ((pf + (spinfo->last_pf << 3)) / 9)
191 >> RC_PID_ARITH_SHIFT; 182 >> RC_PID_ARITH_SHIFT;
192 } 183 }
193 184
@@ -195,16 +186,16 @@ static void rate_control_pid_sample(struct rc_pid_info *pinfo,
195 spinfo->tx_num_failed = 0; 186 spinfo->tx_num_failed = 0;
196 187
197 /* If we just switched rate, update the rate behaviour info. */ 188 /* If we just switched rate, update the rate behaviour info. */
198 if (pinfo->oldrate != sta->txrate_idx) { 189 if (pinfo->oldrate != spinfo->txrate_idx) {
199 190
200 i = rinfo[pinfo->oldrate].rev_index; 191 i = rinfo[pinfo->oldrate].rev_index;
201 j = rinfo[sta->txrate_idx].rev_index; 192 j = rinfo[spinfo->txrate_idx].rev_index;
202 193
203 tmp = (pf - spinfo->last_pf); 194 tmp = (pf - spinfo->last_pf);
204 tmp = RC_PID_DO_ARITH_RIGHT_SHIFT(tmp, RC_PID_ARITH_SHIFT); 195 tmp = RC_PID_DO_ARITH_RIGHT_SHIFT(tmp, RC_PID_ARITH_SHIFT);
205 196
206 rinfo[j].diff = rinfo[i].diff + tmp; 197 rinfo[j].diff = rinfo[i].diff + tmp;
207 pinfo->oldrate = sta->txrate_idx; 198 pinfo->oldrate = spinfo->txrate_idx;
208 } 199 }
209 rate_control_pid_normalize(pinfo, sband->n_bitrates); 200 rate_control_pid_normalize(pinfo, sband->n_bitrates);
210 201
@@ -233,43 +224,26 @@ static void rate_control_pid_sample(struct rc_pid_info *pinfo,
233 224
234 /* Change rate. */ 225 /* Change rate. */
235 if (adj) 226 if (adj)
236 rate_control_pid_adjust_rate(local, sta, adj, rinfo); 227 rate_control_pid_adjust_rate(sband, sta, spinfo, adj, rinfo);
237} 228}
238 229
239static void rate_control_pid_tx_status(void *priv, struct net_device *dev, 230static void rate_control_pid_tx_status(void *priv, struct ieee80211_supported_band *sband,
231 struct ieee80211_sta *sta, void *priv_sta,
240 struct sk_buff *skb) 232 struct sk_buff *skb)
241{ 233{
242 struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
243 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
244 struct ieee80211_sub_if_data *sdata;
245 struct rc_pid_info *pinfo = priv; 234 struct rc_pid_info *pinfo = priv;
246 struct sta_info *sta; 235 struct rc_pid_sta_info *spinfo = priv_sta;
247 struct rc_pid_sta_info *spinfo;
248 unsigned long period; 236 unsigned long period;
249 struct ieee80211_supported_band *sband;
250 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); 237 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
251 238
252 rcu_read_lock(); 239 if (!spinfo)
253 240 return;
254 sta = sta_info_get(local, hdr->addr1);
255 sband = local->hw.wiphy->bands[local->hw.conf.channel->band];
256
257 if (!sta)
258 goto unlock;
259
260 /* Don't update the state if we're not controlling the rate. */
261 sdata = sta->sdata;
262 if (sdata->force_unicast_rateidx > -1) {
263 sta->txrate_idx = sdata->max_ratectrl_rateidx;
264 goto unlock;
265 }
266 241
267 /* Ignore all frames that were sent with a different rate than the rate 242 /* Ignore all frames that were sent with a different rate than the rate
268 * we currently advise mac80211 to use. */ 243 * we currently advise mac80211 to use. */
269 if (info->tx_rate_idx != sta->txrate_idx) 244 if (info->tx_rate_idx != spinfo->txrate_idx)
270 goto unlock; 245 return;
271 246
272 spinfo = sta->rate_ctrl_priv;
273 spinfo->tx_num_xmit++; 247 spinfo->tx_num_xmit++;
274 248
275#ifdef CONFIG_MAC80211_DEBUGFS 249#ifdef CONFIG_MAC80211_DEBUGFS
@@ -287,93 +261,68 @@ static void rate_control_pid_tx_status(void *priv, struct net_device *dev,
287 spinfo->tx_num_xmit++; 261 spinfo->tx_num_xmit++;
288 } 262 }
289 263
290 if (info->status.excessive_retries) {
291 sta->tx_retry_failed++;
292 sta->tx_num_consecutive_failures++;
293 sta->tx_num_mpdu_fail++;
294 } else {
295 sta->tx_num_consecutive_failures = 0;
296 sta->tx_num_mpdu_ok++;
297 }
298 sta->tx_retry_count += info->status.retry_count;
299 sta->tx_num_mpdu_fail += info->status.retry_count;
300
301 /* Update PID controller state. */ 264 /* Update PID controller state. */
302 period = (HZ * pinfo->sampling_period + 500) / 1000; 265 period = (HZ * pinfo->sampling_period + 500) / 1000;
303 if (!period) 266 if (!period)
304 period = 1; 267 period = 1;
305 if (time_after(jiffies, spinfo->last_sample + period)) 268 if (time_after(jiffies, spinfo->last_sample + period))
306 rate_control_pid_sample(pinfo, local, sta); 269 rate_control_pid_sample(pinfo, sband, sta, spinfo);
307
308 unlock:
309 rcu_read_unlock();
310} 270}
311 271
312static void rate_control_pid_get_rate(void *priv, struct net_device *dev, 272static void
313 struct ieee80211_supported_band *sband, 273rate_control_pid_get_rate(void *priv, struct ieee80211_supported_band *sband,
314 struct sk_buff *skb, 274 struct ieee80211_sta *sta, void *priv_sta,
315 struct rate_selection *sel) 275 struct sk_buff *skb,
276 struct rate_selection *sel)
316{ 277{
317 struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
318 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; 278 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
319 struct ieee80211_sub_if_data *sdata; 279 struct rc_pid_sta_info *spinfo = priv_sta;
320 struct sta_info *sta;
321 int rateidx; 280 int rateidx;
322 u16 fc; 281 u16 fc;
323 282
324 rcu_read_lock();
325
326 sta = sta_info_get(local, hdr->addr1);
327
328 /* Send management frames and broadcast/multicast data using lowest 283 /* Send management frames and broadcast/multicast data using lowest
329 * rate. */ 284 * rate. */
330 fc = le16_to_cpu(hdr->frame_control); 285 fc = le16_to_cpu(hdr->frame_control);
331 if ((fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA || 286 if (!sta || !spinfo ||
332 is_multicast_ether_addr(hdr->addr1) || !sta) { 287 (fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA ||
333 sel->rate_idx = rate_lowest_index(local, sband, sta); 288 is_multicast_ether_addr(hdr->addr1)) {
334 rcu_read_unlock(); 289 sel->rate_idx = rate_lowest_index(sband, sta);
335 return; 290 return;
336 } 291 }
337 292
338 /* If a forced rate is in effect, select it. */ 293 rateidx = spinfo->txrate_idx;
339 sdata = IEEE80211_DEV_TO_SUB_IF(dev);
340 if (sdata->force_unicast_rateidx > -1)
341 sta->txrate_idx = sdata->force_unicast_rateidx;
342
343 rateidx = sta->txrate_idx;
344 294
345 if (rateidx >= sband->n_bitrates) 295 if (rateidx >= sband->n_bitrates)
346 rateidx = sband->n_bitrates - 1; 296 rateidx = sband->n_bitrates - 1;
347 297
348 sta->last_txrate_idx = rateidx;
349
350 rcu_read_unlock();
351
352 sel->rate_idx = rateidx; 298 sel->rate_idx = rateidx;
353 299
354#ifdef CONFIG_MAC80211_DEBUGFS 300#ifdef CONFIG_MAC80211_DEBUGFS
355 rate_control_pid_event_tx_rate( 301 rate_control_pid_event_tx_rate(&spinfo->events,
356 &((struct rc_pid_sta_info *) sta->rate_ctrl_priv)->events,
357 rateidx, sband->bitrates[rateidx].bitrate); 302 rateidx, sband->bitrates[rateidx].bitrate);
358#endif 303#endif
359} 304}
360 305
361static void rate_control_pid_rate_init(void *priv, void *priv_sta, 306static void
362 struct ieee80211_local *local, 307rate_control_pid_rate_init(void *priv, struct ieee80211_supported_band *sband,
363 struct sta_info *sta) 308 struct ieee80211_sta *sta, void *priv_sta)
364{ 309{
310 struct rc_pid_sta_info *spinfo = priv_sta;
311 struct sta_info *si;
312
365 /* TODO: This routine should consider using RSSI from previous packets 313 /* TODO: This routine should consider using RSSI from previous packets
366 * as we need to have IEEE 802.1X auth succeed immediately after assoc.. 314 * as we need to have IEEE 802.1X auth succeed immediately after assoc..
367 * Until that method is implemented, we will use the lowest supported 315 * Until that method is implemented, we will use the lowest supported
368 * rate as a workaround. */ 316 * rate as a workaround. */
369 struct ieee80211_supported_band *sband;
370 317
371 sband = local->hw.wiphy->bands[local->hw.conf.channel->band]; 318 spinfo->txrate_idx = rate_lowest_index(sband, sta);
372 sta->txrate_idx = rate_lowest_index(local, sband, sta); 319 /* HACK */
373 sta->fail_avg = 0; 320 si = container_of(sta, struct sta_info, sta);
321 si->fail_avg = 0;
374} 322}
375 323
376static void *rate_control_pid_alloc(struct ieee80211_local *local) 324static void *rate_control_pid_alloc(struct ieee80211_hw *hw,
325 struct dentry *debugfsdir)
377{ 326{
378 struct rc_pid_info *pinfo; 327 struct rc_pid_info *pinfo;
379 struct rc_pid_rateinfo *rinfo; 328 struct rc_pid_rateinfo *rinfo;
@@ -384,7 +333,7 @@ static void *rate_control_pid_alloc(struct ieee80211_local *local)
384 struct rc_pid_debugfs_entries *de; 333 struct rc_pid_debugfs_entries *de;
385#endif 334#endif
386 335
387 sband = local->hw.wiphy->bands[local->hw.conf.channel->band]; 336 sband = hw->wiphy->bands[hw->conf.channel->band];
388 337
389 pinfo = kmalloc(sizeof(*pinfo), GFP_ATOMIC); 338 pinfo = kmalloc(sizeof(*pinfo), GFP_ATOMIC);
390 if (!pinfo) 339 if (!pinfo)
@@ -439,30 +388,28 @@ static void *rate_control_pid_alloc(struct ieee80211_local *local)
439 388
440#ifdef CONFIG_MAC80211_DEBUGFS 389#ifdef CONFIG_MAC80211_DEBUGFS
441 de = &pinfo->dentries; 390 de = &pinfo->dentries;
442 de->dir = debugfs_create_dir("rc80211_pid",
443 local->hw.wiphy->debugfsdir);
444 de->target = debugfs_create_u32("target_pf", S_IRUSR | S_IWUSR, 391 de->target = debugfs_create_u32("target_pf", S_IRUSR | S_IWUSR,
445 de->dir, &pinfo->target); 392 debugfsdir, &pinfo->target);
446 de->sampling_period = debugfs_create_u32("sampling_period", 393 de->sampling_period = debugfs_create_u32("sampling_period",
447 S_IRUSR | S_IWUSR, de->dir, 394 S_IRUSR | S_IWUSR, debugfsdir,
448 &pinfo->sampling_period); 395 &pinfo->sampling_period);
449 de->coeff_p = debugfs_create_u32("coeff_p", S_IRUSR | S_IWUSR, 396 de->coeff_p = debugfs_create_u32("coeff_p", S_IRUSR | S_IWUSR,
450 de->dir, &pinfo->coeff_p); 397 debugfsdir, &pinfo->coeff_p);
451 de->coeff_i = debugfs_create_u32("coeff_i", S_IRUSR | S_IWUSR, 398 de->coeff_i = debugfs_create_u32("coeff_i", S_IRUSR | S_IWUSR,
452 de->dir, &pinfo->coeff_i); 399 debugfsdir, &pinfo->coeff_i);
453 de->coeff_d = debugfs_create_u32("coeff_d", S_IRUSR | S_IWUSR, 400 de->coeff_d = debugfs_create_u32("coeff_d", S_IRUSR | S_IWUSR,
454 de->dir, &pinfo->coeff_d); 401 debugfsdir, &pinfo->coeff_d);
455 de->smoothing_shift = debugfs_create_u32("smoothing_shift", 402 de->smoothing_shift = debugfs_create_u32("smoothing_shift",
456 S_IRUSR | S_IWUSR, de->dir, 403 S_IRUSR | S_IWUSR, debugfsdir,
457 &pinfo->smoothing_shift); 404 &pinfo->smoothing_shift);
458 de->sharpen_factor = debugfs_create_u32("sharpen_factor", 405 de->sharpen_factor = debugfs_create_u32("sharpen_factor",
459 S_IRUSR | S_IWUSR, de->dir, 406 S_IRUSR | S_IWUSR, debugfsdir,
460 &pinfo->sharpen_factor); 407 &pinfo->sharpen_factor);
461 de->sharpen_duration = debugfs_create_u32("sharpen_duration", 408 de->sharpen_duration = debugfs_create_u32("sharpen_duration",
462 S_IRUSR | S_IWUSR, de->dir, 409 S_IRUSR | S_IWUSR, debugfsdir,
463 &pinfo->sharpen_duration); 410 &pinfo->sharpen_duration);
464 de->norm_offset = debugfs_create_u32("norm_offset", 411 de->norm_offset = debugfs_create_u32("norm_offset",
465 S_IRUSR | S_IWUSR, de->dir, 412 S_IRUSR | S_IWUSR, debugfsdir,
466 &pinfo->norm_offset); 413 &pinfo->norm_offset);
467#endif 414#endif
468 415
@@ -484,7 +431,6 @@ static void rate_control_pid_free(void *priv)
484 debugfs_remove(de->coeff_p); 431 debugfs_remove(de->coeff_p);
485 debugfs_remove(de->sampling_period); 432 debugfs_remove(de->sampling_period);
486 debugfs_remove(de->target); 433 debugfs_remove(de->target);
487 debugfs_remove(de->dir);
488#endif 434#endif
489 435
490 kfree(pinfo->rinfo); 436 kfree(pinfo->rinfo);
@@ -495,7 +441,8 @@ static void rate_control_pid_clear(void *priv)
495{ 441{
496} 442}
497 443
498static void *rate_control_pid_alloc_sta(void *priv, gfp_t gfp) 444static void *rate_control_pid_alloc_sta(void *priv, struct ieee80211_sta *sta,
445 gfp_t gfp)
499{ 446{
500 struct rc_pid_sta_info *spinfo; 447 struct rc_pid_sta_info *spinfo;
501 448
@@ -513,10 +460,10 @@ static void *rate_control_pid_alloc_sta(void *priv, gfp_t gfp)
513 return spinfo; 460 return spinfo;
514} 461}
515 462
516static void rate_control_pid_free_sta(void *priv, void *priv_sta) 463static void rate_control_pid_free_sta(void *priv, struct ieee80211_sta *sta,
464 void *priv_sta)
517{ 465{
518 struct rc_pid_sta_info *spinfo = priv_sta; 466 kfree(priv_sta);
519 kfree(spinfo);
520} 467}
521 468
522static struct rate_control_ops mac80211_rcpid = { 469static struct rate_control_ops mac80211_rcpid = {