aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/net/wireless/ath/ath5k/base.c11
-rw-r--r--drivers/net/wireless/ath/ath5k/base.h8
-rw-r--r--drivers/net/wireless/ath/ath5k/debug.c106
-rw-r--r--drivers/net/wireless/ath/ath5k/debug.h1
4 files changed, 126 insertions, 0 deletions
diff --git a/drivers/net/wireless/ath/ath5k/base.c b/drivers/net/wireless/ath/ath5k/base.c
index 7c08434ebd1..e7a989c707a 100644
--- a/drivers/net/wireless/ath/ath5k/base.c
+++ b/drivers/net/wireless/ath/ath5k/base.c
@@ -1997,6 +1997,12 @@ accept:
1997 rxs->signal = rxs->noise + rs.rs_rssi; 1997 rxs->signal = rxs->noise + rs.rs_rssi;
1998 1998
1999 rxs->antenna = rs.rs_antenna; 1999 rxs->antenna = rs.rs_antenna;
2000
2001 if (rs.rs_antenna > 0 && rs.rs_antenna < 5)
2002 sc->stats.antenna_rx[rs.rs_antenna]++;
2003 else
2004 sc->stats.antenna_rx[0]++; /* invalid */
2005
2000 rxs->rate_idx = ath5k_hw_to_driver_rix(sc, rs.rs_rate); 2006 rxs->rate_idx = ath5k_hw_to_driver_rix(sc, rs.rs_rate);
2001 rxs->flag |= ath5k_rx_decrypted(sc, ds, skb, &rs); 2007 rxs->flag |= ath5k_rx_decrypted(sc, ds, skb, &rs);
2002 2008
@@ -2090,6 +2096,11 @@ ath5k_tx_processq(struct ath5k_softc *sc, struct ath5k_txq *txq)
2090 */ 2096 */
2091 ath5k_remove_padding(skb); 2097 ath5k_remove_padding(skb);
2092 2098
2099 if (ts.ts_antenna > 0 && ts.ts_antenna < 5)
2100 sc->stats.antenna_tx[ts.ts_antenna]++;
2101 else
2102 sc->stats.antenna_tx[0]++; /* invalid */
2103
2093 ieee80211_tx_status(sc->hw, skb); 2104 ieee80211_tx_status(sc->hw, skb);
2094 2105
2095 spin_lock(&sc->txbuflock); 2106 spin_lock(&sc->txbuflock);
diff --git a/drivers/net/wireless/ath/ath5k/base.h b/drivers/net/wireless/ath/ath5k/base.h
index 7e1a88a5abd..ca525842d82 100644
--- a/drivers/net/wireless/ath/ath5k/base.h
+++ b/drivers/net/wireless/ath/ath5k/base.h
@@ -105,6 +105,12 @@ struct ath5k_rfkill {
105 struct tasklet_struct toggleq; 105 struct tasklet_struct toggleq;
106}; 106};
107 107
108/* statistics (only used for debugging now) */
109struct ath5k_statistics {
110 unsigned int antenna_rx[5]; /* frames count per antenna RX */
111 unsigned int antenna_tx[5]; /* frames count per antenna TX */
112};
113
108#if CHAN_DEBUG 114#if CHAN_DEBUG
109#define ATH_CHAN_MAX (26+26+26+200+200) 115#define ATH_CHAN_MAX (26+26+26+200+200)
110#else 116#else
@@ -191,6 +197,8 @@ struct ath5k_softc {
191 int power_level; /* Requested tx power in dbm */ 197 int power_level; /* Requested tx power in dbm */
192 bool assoc; /* associate state */ 198 bool assoc; /* associate state */
193 bool enable_beacon; /* true if beacons are on */ 199 bool enable_beacon; /* true if beacons are on */
200
201 struct ath5k_statistics stats;
194}; 202};
195 203
196#define ath5k_hw_hasbssidmask(_ah) \ 204#define ath5k_hw_hasbssidmask(_ah) \
diff --git a/drivers/net/wireless/ath/ath5k/debug.c b/drivers/net/wireless/ath/ath5k/debug.c
index 747508c15d3..236f20f9cd4 100644
--- a/drivers/net/wireless/ath/ath5k/debug.c
+++ b/drivers/net/wireless/ath/ath5k/debug.c
@@ -364,6 +364,107 @@ static const struct file_operations fops_debug = {
364}; 364};
365 365
366 366
367/* debugfs: antenna */
368
369static ssize_t read_file_antenna(struct file *file, char __user *user_buf,
370 size_t count, loff_t *ppos)
371{
372 struct ath5k_softc *sc = file->private_data;
373 char buf[700];
374 unsigned int len = 0;
375 unsigned int i;
376 unsigned int v;
377
378 len += snprintf(buf+len, sizeof(buf)-len, "antenna mode\t%d\n",
379 sc->ah->ah_ant_mode);
380 len += snprintf(buf+len, sizeof(buf)-len, "default antenna\t%d\n",
381 sc->ah->ah_def_ant);
382 len += snprintf(buf+len, sizeof(buf)-len, "tx antenna\t%d\n",
383 sc->ah->ah_tx_ant);
384
385 len += snprintf(buf+len, sizeof(buf)-len, "\nANTENNA\t\tRX\tTX\n");
386 for (i = 1; i < ARRAY_SIZE(sc->stats.antenna_rx); i++) {
387 len += snprintf(buf+len, sizeof(buf)-len,
388 "[antenna %d]\t%d\t%d\n",
389 i, sc->stats.antenna_rx[i], sc->stats.antenna_tx[i]);
390 }
391 len += snprintf(buf+len, sizeof(buf)-len, "[invalid]\t%d\t%d\n",
392 sc->stats.antenna_rx[0], sc->stats.antenna_tx[0]);
393
394 v = ath5k_hw_reg_read(sc->ah, AR5K_DEFAULT_ANTENNA);
395 len += snprintf(buf+len, sizeof(buf)-len,
396 "\nAR5K_DEFAULT_ANTENNA\t0x%08x\n", v);
397
398 v = ath5k_hw_reg_read(sc->ah, AR5K_STA_ID1);
399 len += snprintf(buf+len, sizeof(buf)-len,
400 "AR5K_STA_ID1_DEFAULT_ANTENNA\t%d\n",
401 (v & AR5K_STA_ID1_DEFAULT_ANTENNA) != 0);
402 len += snprintf(buf+len, sizeof(buf)-len,
403 "AR5K_STA_ID1_DESC_ANTENNA\t%d\n",
404 (v & AR5K_STA_ID1_DESC_ANTENNA) != 0);
405 len += snprintf(buf+len, sizeof(buf)-len,
406 "AR5K_STA_ID1_RTS_DEF_ANTENNA\t%d\n",
407 (v & AR5K_STA_ID1_RTS_DEF_ANTENNA) != 0);
408 len += snprintf(buf+len, sizeof(buf)-len,
409 "AR5K_STA_ID1_SELFGEN_DEF_ANT\t%d\n",
410 (v & AR5K_STA_ID1_SELFGEN_DEF_ANT) != 0);
411
412 v = ath5k_hw_reg_read(sc->ah, AR5K_PHY_AGCCTL);
413 len += snprintf(buf+len, sizeof(buf)-len,
414 "\nAR5K_PHY_AGCCTL_OFDM_DIV_DIS\t%d\n",
415 (v & AR5K_PHY_AGCCTL_OFDM_DIV_DIS) != 0);
416
417 v = ath5k_hw_reg_read(sc->ah, AR5K_PHY_RESTART);
418 len += snprintf(buf+len, sizeof(buf)-len,
419 "AR5K_PHY_RESTART_DIV_GC\t\t%x\n",
420 (v & AR5K_PHY_RESTART_DIV_GC) >> AR5K_PHY_RESTART_DIV_GC_S);
421
422 v = ath5k_hw_reg_read(sc->ah, AR5K_PHY_FAST_ANT_DIV);
423 len += snprintf(buf+len, sizeof(buf)-len,
424 "AR5K_PHY_FAST_ANT_DIV_EN\t%d\n",
425 (v & AR5K_PHY_FAST_ANT_DIV_EN) != 0);
426
427 return simple_read_from_buffer(user_buf, count, ppos, buf, len);
428}
429
430static ssize_t write_file_antenna(struct file *file,
431 const char __user *userbuf,
432 size_t count, loff_t *ppos)
433{
434 struct ath5k_softc *sc = file->private_data;
435 unsigned int i;
436 char buf[20];
437
438 if (copy_from_user(buf, userbuf, min(count, sizeof(buf))))
439 return -EFAULT;
440
441 if (strncmp(buf, "diversity", 9) == 0) {
442 ath5k_hw_set_antenna_mode(sc->ah, AR5K_ANTMODE_DEFAULT);
443 printk(KERN_INFO "ath5k debug: enable diversity\n");
444 } else if (strncmp(buf, "fixed-a", 7) == 0) {
445 ath5k_hw_set_antenna_mode(sc->ah, AR5K_ANTMODE_FIXED_A);
446 printk(KERN_INFO "ath5k debugfs: fixed antenna A\n");
447 } else if (strncmp(buf, "fixed-b", 7) == 0) {
448 ath5k_hw_set_antenna_mode(sc->ah, AR5K_ANTMODE_FIXED_B);
449 printk(KERN_INFO "ath5k debug: fixed antenna B\n");
450 } else if (strncmp(buf, "clear", 5) == 0) {
451 for (i = 0; i < ARRAY_SIZE(sc->stats.antenna_rx); i++) {
452 sc->stats.antenna_rx[i] = 0;
453 sc->stats.antenna_tx[i] = 0;
454 }
455 printk(KERN_INFO "ath5k debug: cleared antenna stats\n");
456 }
457 return count;
458}
459
460static const struct file_operations fops_antenna = {
461 .read = read_file_antenna,
462 .write = write_file_antenna,
463 .open = ath5k_debugfs_open,
464 .owner = THIS_MODULE,
465};
466
467
367/* init */ 468/* init */
368 469
369void 470void
@@ -393,6 +494,10 @@ ath5k_debug_init_device(struct ath5k_softc *sc)
393 494
394 sc->debug.debugfs_reset = debugfs_create_file("reset", S_IWUSR, 495 sc->debug.debugfs_reset = debugfs_create_file("reset", S_IWUSR,
395 sc->debug.debugfs_phydir, sc, &fops_reset); 496 sc->debug.debugfs_phydir, sc, &fops_reset);
497
498 sc->debug.debugfs_antenna = debugfs_create_file("antenna",
499 S_IWUSR | S_IRUSR,
500 sc->debug.debugfs_phydir, sc, &fops_antenna);
396} 501}
397 502
398void 503void
@@ -408,6 +513,7 @@ ath5k_debug_finish_device(struct ath5k_softc *sc)
408 debugfs_remove(sc->debug.debugfs_registers); 513 debugfs_remove(sc->debug.debugfs_registers);
409 debugfs_remove(sc->debug.debugfs_beacon); 514 debugfs_remove(sc->debug.debugfs_beacon);
410 debugfs_remove(sc->debug.debugfs_reset); 515 debugfs_remove(sc->debug.debugfs_reset);
516 debugfs_remove(sc->debug.debugfs_antenna);
411 debugfs_remove(sc->debug.debugfs_phydir); 517 debugfs_remove(sc->debug.debugfs_phydir);
412} 518}
413 519
diff --git a/drivers/net/wireless/ath/ath5k/debug.h b/drivers/net/wireless/ath/ath5k/debug.h
index 66f69f04e55..01861271104 100644
--- a/drivers/net/wireless/ath/ath5k/debug.h
+++ b/drivers/net/wireless/ath/ath5k/debug.h
@@ -74,6 +74,7 @@ struct ath5k_dbg_info {
74 struct dentry *debugfs_registers; 74 struct dentry *debugfs_registers;
75 struct dentry *debugfs_beacon; 75 struct dentry *debugfs_beacon;
76 struct dentry *debugfs_reset; 76 struct dentry *debugfs_reset;
77 struct dentry *debugfs_antenna;
77}; 78};
78 79
79/** 80/**